#if defined(TSINGMA_MX) || defined(TSINGMA_GX) || defined(ARCTIC)
#include "ctc_security.h"
#include "sys_usw_scl.h"
#include "sys_usw_register.h"
#include "sys_usw_common.h"
#include "sys_usw_xdata_api.h"


/*Set userid bitmap with check*/
#define SYS_SCL_BIT_SET(bmp, offset, ds, is_set) \
    if(no_aset)\
    {\
        if (is_set) \
            CTC_BIT_SET(bmp, offset);\
        else\
        {\
            uint32* p_temp_fields = SYS_SCL_TEMP_USERID(ds, offset);\
            if (!p_temp_fields[0] && !p_temp_fields[1]) \
                CTC_BIT_UNSET(bmp, offset);\
        }\
    }

#define SYS_TMM_SCL_UPDATE_DSFWD() \
    if (pe->u.temp_entry->temp_ad.nexthop_id && fwd_u_type == SYS_AD_UNION_G_3) \
    { \
        uint32 fwd_offset = 0; \
        /*change to use dsfwd*/ \
        CTC_ERROR_RETURN(sys_usw_nh_get_dsfwd_offset(lchip, pe->u.temp_entry->temp_ad.nexthop_id, &fwd_offset, 0, CTC_FEATURE_SCL)); \
        if(pe->u.temp_entry->temp_ad.bind_nh) \
        { \
            sys_nh_info_dsnh_t dsnh_info; \
            sal_memset(&dsnh_info, 0, sizeof(sys_nh_info_dsnh_t)); \
            CTC_ERROR_RETURN(sys_usw_nh_get_nhinfo(lchip, pe->u.temp_entry->temp_ad.nexthop_id, &dsnh_info, 0)); \
            dsnh_info.merge_dsfwd = 2; \
            dsnh_info.need_lock = 0; \
            MCHIP_SCL(lchip)->update_action(lchip, (void*)pe, (void*)&dsnh_info); \
        }\
        sal_memcpy(&temp_ds_userid, pe->u.temp_entry->action, sizeof(pe->u.temp_entry->action));\
        sys_tmm_scl_move_dsuserid_to_temp(lchip, ds_userid, pe->u.temp_entry->temp_ad.com.userid_bmp);\
        pe->u.temp_entry->temp_ad.bind_nh = 0; \
        fwd_u_type = SYS_AD_UNION_G_NA; \
    }
#define SYS_SET_FK_FIELD(xdata_fk, data, mask)\
    {\
        CTC_ERROR_RETURN(MCHIP_XDATA(lchip)->set_fk_field(lchip, &xdata_fk, p_data, (data)));\
        CTC_ERROR_RETURN(MCHIP_XDATA(lchip)->set_fk_field(lchip, &xdata_fk, p_mask, (mask)));\
    }
#define SYS_GET_FK_FIELD(xdata_fk, data, mask)\
    {\
        CTC_ERROR_RETURN(MCHIP_XDATA(lchip)->get_fk_field(lchip, &xdata_fk, p_data, &(data)));\
        CTC_ERROR_RETURN(MCHIP_XDATA(lchip)->get_fk_field(lchip, &xdata_fk, p_mask, &(mask)));\
    }

struct sys_scl_userid_bitmap_s
{
    uint8   u_type;
    uint8   u1_type;
};
typedef struct sys_scl_userid_bitmap_s sys_scl_userid_bitmap_t;

/**< [TMM]
   userid_bmp: Bit7 ~ Bit0, total 8 bits (used as the index of userid_bmp_db);
   sys_scl_userid_bitmap_t: {u_type, u1_type} (union type: 0 = none, -1 = invalid, others = group id)
   -------------------------------------------------------------------------------------
   | reserved | u1_g1 | Binding | Port Extender | Flow | Logic Port | Vlan Xlate | FWD |
   -------------------------------------------------------------------------------------
*/
sys_scl_userid_bitmap_t const userid_bmp_db[] = { \
{0,0},  {2,0},  {1,0},  {2,0},  {1,0},  {6,0},  {1,0},  {1,4},  {4,0},  {5,0},  {8,0},  {5,3},  {7,0},  {7,4},  {7,3},  {-1,-1}, \
{4,0},  {4,4},  {4,3},  {-1,-1},{-1,-1},{-1,-1},{-1,-1},{-1,-1},{4,0},  {4,4},  {4,3},{-1,-1},{-1,-1},{-1,-1},{-1,-1},{-1,-1}, \
{3,0},  {3,0},  {3,3},  {3,3},{-1,-1},{-1,-1},{-1,-1},{-1,-1},  {3,2},  {3,2},{-1,-1},{-1,-1},{-1,-1},{-1,-1},{-1,-1},{-1,-1}, \
{-1,-1},{-1,-1},{-1,-1},{-1,-1},{-1,-1},{-1,-1},{-1,-1},{-1,-1},{-1,-1},{-1,-1},{-1,-1},{-1,-1},{-1,-1},{-1,-1},{-1,-1},{-1,-1}, \
{0,1},  {2,1},  {1,1},  {2,1},  {1,1},  {6,1},  {1,1},  {-1,-1},{4,1},  {5,1},  {8,1},  {-1,-1},{7,1},  {-1,-1},{-1,-1},{-1,-1}, \
{4,1},  {-1,-1},{-1,-1},{-1,-1},{-1,-1},{-1,-1},{-1,-1},{-1,-1},{4,1},  {-1,-1},{-1,-1},{-1,-1},{-1,-1},{-1,-1},{-1,-1},{-1,-1}, \
{3,1},  {3,1},  {-1,-1},{-1,-1},{-1,-1},{-1,-1},{-1,-1},{-1,-1},{-1,-1},{-1,-1},{-1,-1},{-1,-1},{-1,-1},{-1,-1},{-1,-1},{-1,-1} };

extern int32
sys_usw_scl_unmapping_vlan_edit(uint8 lchip, ctc_scl_vlan_edit_t* p_vlan_edit,void* p_ds_edit);
extern int32
_sys_usw_scl_remove_old_action(uint8 lchip, ctc_scl_field_action_t* pAction, sys_scl_sw_entry_t* pe, uint32 old_type, uint32 new_type);
extern int32
_sys_usw_scl_build_field_action_igs_cancel_all(uint8 lchip, ctc_scl_field_action_t* pAction, sys_scl_sw_entry_t* pe, uint8 is_add);
extern int32
_sys_usw_scl_unbind_nexthop(uint8 lchip, sys_scl_sw_entry_t* pe, uint32 nh_id);
extern int32
_sys_usw_scl_bind_nexthop(uint8 lchip, sys_scl_sw_entry_t* pe,uint32 nh_id);
extern int32
_sys_usw_scl_chk_category_id_union(uint8 lchip, void* ds, uint32 action_filed_type);
extern int32
_sys_usw_scl_get_nodes_by_eid(uint8 lchip, uint32 eid, sys_scl_sw_entry_t** pe);
extern int32
sys_usw_vlan_overlay_get_fid (uint8 lchip,  uint32 vn_id, uint16* p_fid );
extern int32
_sys_usw_scl_map_key_action_type(uint8 lchip, ctc_scl_entry_t * scl_entry, sys_scl_sw_entry_t * pe);
extern int32
_sys_usw_scl_map_sys_to_ctc_key_type(uint8 lchip, uint8 sys_key_type, uint8* ctc_key_type);
int32
sys_usw_vlan_overlay_get_vn_id (uint8 lchip,  uint16 fid, uint32* p_vn_id);
extern int32
sys_usw_vlan_get_maxvid_from_vrange(uint8 lchip, ctc_vlan_range_info_t * vrange_info, ctc_vlan_range_t * vlan_range, bool is_svlan, uint16 * p_max_vid);
extern int32
sys_usw_vlan_get_vlan_range_by_maxvid(uint8 lchip, ctc_vlan_range_info_t * vrange_info, uint16 max_vid, bool is_svlan, ctc_vlan_range_t * p_vlan_range);
extern int32
_sys_usw_scl_map_key_field_type(uint8 lchip, sys_scl_sw_entry_t* pe, uint16 ctc_field_type, uint8* p_sys_field_type);
extern int32
_sys_usw_scl_check_action_type(uint8 lchip, sys_scl_sw_entry_t * pe);





int32
sys_tmm_scl_move_dsuserid_to_temp(uint8 lchip, void* ds, uint8 userid_bmp)
{
    sys_scl_userid_bitmap_t bmp_db;
    uint32  zeros[2] = {0};
    uint32* temp_ds = NULL;
    sal_memcpy(&bmp_db, &userid_bmp_db[userid_bmp], sizeof(sys_scl_userid_bitmap_t));
    switch(bmp_db.u_type)
    {
        case 1:
            GetDsUserId(A, u_g1_logicPort_f, ds, SYS_SCL_TEMP_USERID(ds, SYS_SCL_USERID_BMP_LOGIC_PORT));
            GetDsUserId(A, u_g1_vlanXlate_f, ds, SYS_SCL_TEMP_USERID(ds, SYS_SCL_USERID_BMP_VLAN_XLATE));
            break;
        case 2:
            GetDsUserId(A, u_g2_fwd_f, ds, SYS_SCL_TEMP_USERID(ds, SYS_SCL_USERID_BMP_FWD));
            GetDsUserId(A, u_g2_vlanXlate_f, ds, SYS_SCL_TEMP_USERID(ds, SYS_SCL_USERID_BMP_VLAN_XLATE));
            break;
        case 3:
            GetDsUserId(A, u_g3_binding_f, ds, SYS_SCL_TEMP_USERID(ds, SYS_SCL_USERID_BMP_BINDING));
            GetDsUserId(A, u_g3_fwd_f, ds, SYS_SCL_TEMP_USERID(ds, SYS_SCL_USERID_BMP_FWD));
            break;
        case 4:
            GetDsUserId(A, u_g4_flow_f, ds, SYS_SCL_TEMP_USERID(ds, SYS_SCL_USERID_BMP_FLOW));
            GetDsUserId(A, u_g4_portExtender_f, ds, SYS_SCL_TEMP_USERID(ds, SYS_SCL_USERID_BMP_PORT_EXTENDER));
            temp_ds = SYS_SCL_TEMP_USERID(ds, SYS_SCL_USERID_BMP_PORT_EXTENDER);
            temp_ds[1] = GetDsUserId(V, u_g4_routerMac_f, ds);
            if (GetDsUserId(V, u_g4_routerMacHit_f, ds))
            {
                CTC_BIT_SET(temp_ds[1], SYS_SCL_USERID_ROUTER_MAC_HIT_BASE);
            }
            else
            {
                CTC_BIT_UNSET(temp_ds[1], SYS_SCL_USERID_ROUTER_MAC_HIT_BASE);
            }
            break;
        case 5:
            GetDsUserId(A, u_g5_flow_f, ds, SYS_SCL_TEMP_USERID(ds, SYS_SCL_USERID_BMP_FLOW));
            GetDsUserId(A, u_g5_fwd_f, ds, SYS_SCL_TEMP_USERID(ds, SYS_SCL_USERID_BMP_FWD));
            break;
        case 6:
            GetDsUserId(A, u_g6_fwd_f, ds, SYS_SCL_TEMP_USERID(ds, SYS_SCL_USERID_BMP_FWD));
            GetDsUserId(A, u_g6_logicPort_f, ds, SYS_SCL_TEMP_USERID(ds, SYS_SCL_USERID_BMP_LOGIC_PORT));
            break;
        case 7:
            GetDsUserId(A, u_g7_flow_f, ds, SYS_SCL_TEMP_USERID(ds, SYS_SCL_USERID_BMP_FLOW));
            GetDsUserId(A, u_g7_logicPort_f, ds, SYS_SCL_TEMP_USERID(ds, SYS_SCL_USERID_BMP_LOGIC_PORT));
            break;
        case 8:
            GetDsUserId(A, u_g8_flow_f, ds, SYS_SCL_TEMP_USERID(ds, SYS_SCL_USERID_BMP_FLOW));
            GetDsUserId(A, u_g8_vlanXlate_f, ds, SYS_SCL_TEMP_USERID(ds, SYS_SCL_USERID_BMP_VLAN_XLATE));
            break;
        default:
            break;
    }
    SetDsUserId(A, u_g7_flow_f, ds, zeros);
    SetDsUserId(A, u_g7_logicPort_f, ds, zeros);
    switch(bmp_db.u1_type)
    {
        case 1:
            GetDsUserId(A, u1_data_f, ds, SYS_SCL_TEMP_USERID(ds, SYS_SCL_USERID_BMP_U1_G1));
            break;
        case 2:
            GetDsUserId(A, u1_g2_flow_f, ds, SYS_SCL_TEMP_USERID(ds, SYS_SCL_USERID_BMP_FLOW));
            break;
        case 3:
            GetDsUserId(A, u1_g3_vlanXlate_f, ds, SYS_SCL_TEMP_USERID(ds, SYS_SCL_USERID_BMP_VLAN_XLATE));
            break;
        case 4:
            GetDsUserId(A, u1_g4_fwd_f, ds, SYS_SCL_TEMP_USERID(ds, SYS_SCL_USERID_BMP_FWD));
            break;
        default:
            break;
    }
    if (1 != bmp_db.u1_type)
    {
        SetDsUserId(A, u1_data_f, ds, zeros);
    }
    SetDsUserId(V, u1Type_f, ds, 0);    /*Set to default, spec is 3*/
    SetDsUserId(V, uType_f, ds, 0);     /*Set to default*/
    return CTC_E_NONE;
}

int32
_sys_tmm_scl_move_temp_to_dsuserid(uint8 lchip, void* ds, uint8 userid_bmp)
{
    sys_scl_userid_bitmap_t bmp_db;
    uint32  zeros[2] = {0};
    uint32* temp_ds = NULL;
    sal_memcpy(&bmp_db, &userid_bmp_db[userid_bmp], sizeof(sys_scl_userid_bitmap_t));
    SYS_SCL_DBG_OUT(CTC_DEBUG_LEVEL_INFO, "###### utype:%u, u1type:%u ######\n", bmp_db.u_type, bmp_db.u1_type);
    switch(bmp_db.u_type)
    {
        case 1:
            SetDsUserId(A, u_g1_logicPort_f, ds, SYS_SCL_TEMP_USERID(ds, SYS_SCL_USERID_BMP_LOGIC_PORT));
            SetDsUserId(A, u_g1_vlanXlate_f, ds, SYS_SCL_TEMP_USERID(ds, SYS_SCL_USERID_BMP_VLAN_XLATE));
            SetDsUserId(V, uType_f, ds, 0);
            break;
        case 2:
            SetDsUserId(A, u_g2_fwd_f, ds, SYS_SCL_TEMP_USERID(ds, SYS_SCL_USERID_BMP_FWD));
            SetDsUserId(A, u_g2_vlanXlate_f, ds, SYS_SCL_TEMP_USERID(ds, SYS_SCL_USERID_BMP_VLAN_XLATE));
            SetDsUserId(V, uType_f, ds, 1);
            break;
        case 3:
            SetDsUserId(A, u_g3_binding_f, ds, SYS_SCL_TEMP_USERID(ds, SYS_SCL_USERID_BMP_BINDING));
            SetDsUserId(A, u_g3_fwd_f, ds, SYS_SCL_TEMP_USERID(ds, SYS_SCL_USERID_BMP_FWD));
            SetDsUserId(V, uType_f, ds, 2);
            break;
        case 4:
            SetDsUserId(A, u_g4_flow_f, ds, SYS_SCL_TEMP_USERID(ds, SYS_SCL_USERID_BMP_FLOW));
            SetDsUserId(A, u_g4_portExtender_f, ds, SYS_SCL_TEMP_USERID(ds, SYS_SCL_USERID_BMP_PORT_EXTENDER));
            temp_ds = SYS_SCL_TEMP_USERID(ds, SYS_SCL_USERID_BMP_PORT_EXTENDER);
            SetDsUserId(V, u_g4_routerMacHit_f, ds, CTC_IS_BIT_SET(temp_ds[1], SYS_SCL_USERID_ROUTER_MAC_HIT_BASE));
            SetDsUserId(V, u_g4_routerMac_f, ds, temp_ds[1]);
            SetDsUserId(V, uType_f, ds, 3);
            break;
        case 5:
            SetDsUserId(A, u_g5_flow_f, ds, SYS_SCL_TEMP_USERID(ds, SYS_SCL_USERID_BMP_FLOW));
            SetDsUserId(A, u_g5_fwd_f, ds, SYS_SCL_TEMP_USERID(ds, SYS_SCL_USERID_BMP_FWD));
            SetDsUserId(V, uType_f, ds, 4);
            break;
        case 6:
            SetDsUserId(A, u_g6_fwd_f, ds, SYS_SCL_TEMP_USERID(ds, SYS_SCL_USERID_BMP_FWD));
            SetDsUserId(A, u_g6_logicPort_f, ds, SYS_SCL_TEMP_USERID(ds, SYS_SCL_USERID_BMP_LOGIC_PORT));
            SetDsUserId(V, uType_f, ds, 5);
            break;
        case 7:
            SetDsUserId(A, u_g7_flow_f, ds, SYS_SCL_TEMP_USERID(ds, SYS_SCL_USERID_BMP_FLOW));
            SetDsUserId(A, u_g7_logicPort_f, ds, SYS_SCL_TEMP_USERID(ds, SYS_SCL_USERID_BMP_LOGIC_PORT));
            SetDsUserId(V, uType_f, ds, 6);
            break;
        case 8:
            SetDsUserId(A, u_g8_flow_f, ds, SYS_SCL_TEMP_USERID(ds, SYS_SCL_USERID_BMP_FLOW));
            SetDsUserId(A, u_g8_vlanXlate_f, ds, SYS_SCL_TEMP_USERID(ds, SYS_SCL_USERID_BMP_VLAN_XLATE));
            SetDsUserId(V, uType_f, ds, 7);
            break;
        default:
            break;
    }
    switch(bmp_db.u1_type)
    {
        case 1:
            SetDsUserId(V, u1Type_f, ds, 0);
            break;
        case 2:
            SetDsUserId(A, u1_g2_flow_f, ds, SYS_SCL_TEMP_USERID(ds, SYS_SCL_USERID_BMP_FLOW));
            SetDsUserId(V, u1Type_f, ds, 1);
            break;
        case 3:
            SetDsUserId(A, u1_g3_vlanXlate_f, ds, SYS_SCL_TEMP_USERID(ds, SYS_SCL_USERID_BMP_VLAN_XLATE));
            SetDsUserId(V, u1Type_f, ds, 2);
            break;
        case 4:
            SetDsUserId(A, u1_g4_fwd_f, ds, SYS_SCL_TEMP_USERID(ds, SYS_SCL_USERID_BMP_FWD));
            SetDsUserId(V, u1Type_f, ds, 3);
            break;
        default:
            break;
    }
    sal_memcpy(SYS_SCL_TEMP_USERID(ds, SYS_SCL_USERID_BMP_FWD), zeros, sizeof(zeros));
    sal_memcpy(SYS_SCL_TEMP_USERID(ds, SYS_SCL_USERID_BMP_VLAN_XLATE), zeros, sizeof(zeros));
    sal_memcpy(SYS_SCL_TEMP_USERID(ds, SYS_SCL_USERID_BMP_LOGIC_PORT), zeros, sizeof(zeros));
    sal_memcpy(SYS_SCL_TEMP_USERID(ds, SYS_SCL_USERID_BMP_FLOW), zeros, sizeof(zeros));
    sal_memcpy(SYS_SCL_TEMP_USERID(ds, SYS_SCL_USERID_BMP_PORT_EXTENDER), zeros, sizeof(zeros));
    sal_memcpy(SYS_SCL_TEMP_USERID(ds, SYS_SCL_USERID_BMP_BINDING), zeros, sizeof(zeros));
    /*sal_memcpy(SYS_SCL_TEMP_USERID(ds, SYS_SCL_USERID_BMP_U1_G1), zeros, sizeof(zeros));*/
    return CTC_E_NONE;
}

/* pe only valid for read */
STATIC int32
_sys_tmm_scl_map_action_field_to_userid_bmp(uint8 lchip, ctc_scl_field_action_t* pAction, sys_scl_sw_entry_t* pe, void* dsuserid, uint8* p_userid_bmp, uint8 is_add)
{
    uint8 userid_bitmap = *p_userid_bmp;
    uint8 action_type = pe->action_type;
    uint32 temp_data = 0;
    uint32 chunk_bmp = 0;
    void* ds = is_add? (void*)&temp_data: dsuserid;
    uint32 field_type = pAction->type;
    uint8  no_aset = 1;

    if(DRV_FROM_AT(lchip) && (CTC_BMP_ISSET(pe->action_bmp, CTC_SCL_FIELD_ACTION_TYPE_XDATA) || CTC_SCL_FIELD_ACTION_TYPE_XDATA == field_type ))
    {
        CTC_ERROR_RETURN(_sys_usw_scl_check_xdata(lchip,pe,pAction,pe->u.temp_entry->action,is_add,&chunk_bmp)); 
    }
    switch(field_type)
    {
        case CTC_SCL_FIELD_ACTION_TYPE_XDATA:
            if(CTC_FLAG_ISSET(chunk_bmp,SYS_SCL_XDATA_IGS_CHUNK1_NIBBLE3_0))
            {
               SYS_SCL_BIT_SET(userid_bitmap, SYS_SCL_USERID_BMP_U1_G1, ds, is_add);
            }
            break;
        case SYS_SCL_FIELD_ACTION_TYPE_ACTION_COMMON:
        case SYS_SCL_FIELD_ACTION_TYPE_IS_HALF:
        case CTC_SCL_FIELD_ACTION_TYPE_POLICER_ID:
        case CTC_SCL_FIELD_ACTION_TYPE_COS_HBWP_POLICER:
        case CTC_SCL_FIELD_ACTION_TYPE_SERVICE_ID:
        case CTC_SCL_FIELD_ACTION_TYPE_STATS:
        case CTC_SCL_FIELD_ACTION_TYPE_SRC_CID:
        case CTC_SCL_FIELD_ACTION_TYPE_DST_CID:
        case SYS_SCL_FIELD_ACTION_TYPE_VPLS:
        case SYS_SCL_FIELD_ACTION_TYPE_VPWS:
        case CTC_SCL_FIELD_ACTION_TYPE_ETREE_LEAF:
        case CTC_SCL_FIELD_ACTION_TYPE_UDF_ID:
        case CTC_SCL_FIELD_ACTION_TYPE_LOCAL_ARP:
        case CTC_SCL_FIELD_ACTION_TYPE_DENY_BRIDGE:
        case CTC_SCL_FIELD_ACTION_TYPE_DENY_LEARNING:
        case CTC_SCL_FIELD_ACTION_TYPE_DENY_ROUTE:
        /*userid bitmap is belong to pe, pending and cancel all will process alone*/
        case CTC_SCL_FIELD_ACTION_TYPE_PENDING:
        case CTC_SCL_FIELD_ACTION_TYPE_CANCEL_ALL:
            break;
        case CTC_SCL_FIELD_ACTION_TYPE_FLOW_LKUP_BY_OUTER_HEAD:
            if (SYS_SCL_CHK_UNION(pe->u.temp_entry->temp_ad.com.u3_type, SYS_AD_UNION_G_2) && CTC_BMP_ISSET(pe->action_bmp, CTC_SCL_FIELD_ACTION_TYPE_FLOW_LKUP_BY_OUTER_HEAD))
            {
                SYS_SCL_BIT_SET(userid_bitmap, SYS_SCL_USERID_BMP_U1_G1, ds, is_add);
            }
            break;
        case CTC_SCL_FIELD_ACTION_TYPE_IPFIX_LKUP_BY_OUTER_HEAD:
            if (SYS_SCL_CHK_UNION(pe->u.temp_entry->temp_ad.com.u3_type, SYS_AD_UNION_G_2) && CTC_BMP_ISSET(pe->action_bmp, CTC_SCL_FIELD_ACTION_TYPE_IPFIX_LKUP_BY_OUTER_HEAD))
            {
                SYS_SCL_BIT_SET(userid_bitmap, SYS_SCL_USERID_BMP_U1_G1, ds, is_add);
            }
            break;
        case CTC_SCL_FIELD_ACTION_TYPE_FORCE_BRIDGE:
            if (SYS_SCL_CHK_UNION(pe->u.temp_entry->temp_ad.com.u3_type, SYS_AD_UNION_G_2) && CTC_BMP_ISSET(pe->action_bmp, CTC_SCL_FIELD_ACTION_TYPE_FORCE_BRIDGE))
            {
                SYS_SCL_BIT_SET(userid_bitmap, SYS_SCL_USERID_BMP_U1_G1, ds, is_add);
            }
            break;
        case CTC_SCL_FIELD_ACTION_TYPE_FORCE_LEARNING:
            if (SYS_SCL_CHK_UNION(pe->u.temp_entry->temp_ad.com.u3_type, SYS_AD_UNION_G_2) && CTC_BMP_ISSET(pe->action_bmp, CTC_SCL_FIELD_ACTION_TYPE_FORCE_LEARNING))
            {
                SYS_SCL_BIT_SET(userid_bitmap, SYS_SCL_USERID_BMP_U1_G1, ds, is_add);
            }
            break;
        case CTC_SCL_FIELD_ACTION_TYPE_FORCE_ROUTE:
            if (SYS_SCL_CHK_UNION(pe->u.temp_entry->temp_ad.com.u3_type, SYS_AD_UNION_G_2) && CTC_BMP_ISSET(pe->action_bmp, CTC_SCL_FIELD_ACTION_TYPE_FORCE_ROUTE))
            {
                SYS_SCL_BIT_SET(userid_bitmap, SYS_SCL_USERID_BMP_U1_G1, ds, is_add);
            }
            break;
        case CTC_SCL_FIELD_ACTION_TYPE_SERVICE_ACL_EN:
        case SYS_SCL_FIELD_ACTION_TYPE_WLAN_CLIENT:
        case CTC_SCL_FIELD_ACTION_TYPE_MAC_LIMIT_DISCARD_EN:
        case CTC_SCL_FIELD_ACTION_TYPE_ACL_TCAM_EN:
        case CTC_SCL_FIELD_ACTION_TYPE_ACL_HASH_EN:
            return CTC_E_NOT_SUPPORT;
        
        case CTC_SCL_FIELD_ACTION_TYPE_DISCARD:
            SYS_SCL_BIT_SET(userid_bitmap, (SYS_SCL_ACTION_FLOW == action_type)? SYS_SCL_USERID_BMP_FLOW: SYS_SCL_USERID_BMP_FWD, ds, is_add);
            break;
        case CTC_SCL_FIELD_ACTION_TYPE_LOGIC_PORT:
        case CTC_SCL_FIELD_ACTION_TYPE_LOGIC_PORT_TYPE:
        case CTC_SCL_FIELD_ACTION_TYPE_LOGIC_PORT_SECURITY_EN:
        case CTC_SCL_FIELD_ACTION_TYPE_MAC_LIMIT:
        case CTC_SCL_FIELD_ACTION_TYPE_USER_VLANPTR:
        case SYS_SCL_FIELD_ACTION_TYPE_PON_SERVICE:
        case CTC_SCL_FIELD_ACTION_TYPE_QOS_MAP:
            SYS_SCL_BIT_SET(userid_bitmap, SYS_SCL_USERID_BMP_LOGIC_PORT, ds, is_add);
            break;
        case CTC_SCL_FIELD_ACTION_TYPE_METADATA:
            if ((DRV_IS_TMM(lchip) || DRV_IS_TMG(lchip)) || !is_add || SYS_SCL_CHK_UNION(pe->u.temp_entry->temp_ad.com.u2_type ,SYS_AD_UNION_G_2))
            {
                SYS_SCL_BIT_SET(userid_bitmap, SYS_SCL_USERID_BMP_U1_G1, ds, is_add);
            }
            break;
        case CTC_SCL_FIELD_ACTION_TYPE_IGMP_SNOOP_EN:
        case CTC_SCL_FIELD_ACTION_TYPE_STP_ID:
        case CTC_SCL_FIELD_ACTION_TYPE_ARP_ACTION:
        case CTC_SCL_FIELD_ACTION_TYPE_IPV4_BASED_L2MC:
        case CTC_SCL_FIELD_ACTION_TYPE_IPV6_BASED_L2MC:
        //case CTC_SCL_FIELD_ACTION_TYPE_OAM_TUNNEL_EN:
            SYS_SCL_BIT_SET(userid_bitmap, SYS_SCL_USERID_BMP_U1_G1, ds, is_add);
            break;
        case CTC_SCL_FIELD_ACTION_TYPE_APS:
            {
                ctc_scl_aps_t* aps = pAction->ext_data;
                SYS_SCL_BIT_SET(userid_bitmap, SYS_SCL_USERID_BMP_FWD, ds, is_add);
                if (aps && aps->protected_vlan_valid)
                {
                    SYS_SCL_BIT_SET(userid_bitmap, SYS_SCL_USERID_BMP_LOGIC_PORT, ds, is_add);
                }
            }
            break;
        case CTC_SCL_FIELD_ACTION_TYPE_REDIRECT_PORT:
        case CTC_SCL_FIELD_ACTION_TYPE_REDIRECT:
            SYS_SCL_BIT_SET(userid_bitmap, SYS_SCL_USERID_BMP_FWD, ds, is_add);
            SYS_SCL_BIT_SET(userid_bitmap, SYS_SCL_USERID_BMP_LOGIC_PORT, ds, is_add);
            break;
        case CTC_SCL_FIELD_ACTION_TYPE_FID:
        case CTC_SCL_FIELD_ACTION_TYPE_VRFID:
        case SYS_SCL_FIELD_ACTION_TYPE_VN_ID:
        case SYS_SCL_FIELD_ACTION_TYPE_DOT1AE_SCID:
            SYS_SCL_BIT_SET(userid_bitmap, SYS_SCL_USERID_BMP_FWD, ds, is_add);
            break;
        case CTC_SCL_FIELD_ACTION_TYPE_HMAC_ID:
            SYS_SCL_BIT_SET(userid_bitmap, SYS_SCL_USERID_BMP_U1_G1, ds, is_add);
            SYS_SCL_BIT_SET(userid_bitmap, SYS_SCL_USERID_BMP_FWD, ds, is_add);
            break;
        case CTC_SCL_FIELD_ACTION_TYPE_COPY_TO_CPU:
        case CTC_SCL_FIELD_ACTION_TYPE_LB_HASH_SELECT_ID:
        case CTC_SCL_FIELD_ACTION_TYPE_FORCE_DECAP:
        case CTC_SCL_FIELD_ACTION_TYPE_SNOOPING_PARSER:
        case CTC_SCL_FIELD_ACTION_TYPE_FLEX_EDIT:
        case CTC_SCL_FIELD_ACTION_TYPE_L3IF_PROPERTY:
            SYS_SCL_BIT_SET(userid_bitmap, SYS_SCL_USERID_BMP_FLOW, ds, is_add);
            break;
        case SYS_SCL_FIELD_ACTION_TYPE_SRV6:
            {
                sys_scl_srv6_t* srv6 = (sys_scl_srv6_t*)pAction->ext_data;
                SYS_SCL_BIT_SET(userid_bitmap, SYS_SCL_USERID_BMP_FLOW, ds, is_add);
                if(srv6 && srv6->fid)
                {
                    SYS_SCL_BIT_SET(userid_bitmap, SYS_SCL_USERID_BMP_LOGIC_PORT, ds, is_add);
                }
            }
            break;
        case CTC_SCL_FIELD_ACTION_TYPE_VLAN_EDIT:
            SYS_SCL_BIT_SET(userid_bitmap, SYS_SCL_USERID_BMP_VLAN_XLATE, ds, is_add);
            break;
        case CTC_SCL_FIELD_ACTION_TYPE_BINDING_EN:
            SYS_SCL_BIT_SET(userid_bitmap, SYS_SCL_USERID_BMP_BINDING, ds, is_add);
            break;
        case CTC_SCL_FIELD_ACTION_TYPE_OAM:
            SYS_SCL_BIT_SET(userid_bitmap, SYS_SCL_USERID_BMP_LOGIC_PORT, ds, is_add);
            break;
        case CTC_SCL_FIELD_ACTION_TYPE_ROUTER_MAC_MATCH:
            SYS_SCL_BIT_SET(userid_bitmap, SYS_SCL_USERID_BMP_PORT_EXTENDER, ds, is_add);
            break;
        case SYS_SCL_FIELD_ACTION_TYPE_DOT1BR_PE:
            SYS_SCL_BIT_SET(userid_bitmap, SYS_SCL_USERID_BMP_FLOW, ds, is_add);
            SYS_SCL_BIT_SET(userid_bitmap, SYS_SCL_USERID_BMP_PORT_EXTENDER, ds, is_add);
            break;
        default:
            break;
    }
    if (is_add && ( \
       (userid_bitmap<=0x17 && userid_bitmap>=0x13) || (userid_bitmap<=0x1F && userid_bitmap>=0x1B) || \
       (userid_bitmap<=0x27 && userid_bitmap>=0x24) || (userid_bitmap<=0x3F && userid_bitmap>=0x2A) || \
       (userid_bitmap<=0x4F && userid_bitmap>=0x4D) || (userid_bitmap<=0x57 && userid_bitmap>=0x51) || \
       (userid_bitmap<=0x5F && userid_bitmap>=0x59) || (userid_bitmap<=0x7F && userid_bitmap>=0x62) || \
       (userid_bitmap==0x0F) || (userid_bitmap==0x47) || (userid_bitmap==0x4B) ))
    {
        SYS_SCL_DBG_OUT(CTC_DEBUG_LEVEL_ERROR, " %% SCL # userid_bitmap: 0x%X\n", userid_bitmap);
        CTC_ERROR_RETURN(CTC_E_NOT_SUPPORT);
    }
    *p_userid_bmp = userid_bitmap;
    return CTC_E_NONE;
}

int32
sys_tmm_scl_build_hash_key_svlan_dscp_port(uint8 lchip, ctc_field_key_t* pKey, void* pe_info, uint8 is_add)
{
    void*      p_data = NULL;
    void*      p_mask = NULL;
    ctc_field_port_t* p_port = NULL;
    sys_scl_sw_entry_t* pe = (sys_scl_sw_entry_t*)pe_info;

    CTC_PTR_VALID_CHECK(pKey);
    CTC_PTR_VALID_CHECK(pe);
    CTC_PTR_VALID_CHECK(pe->u.temp_entry);

    p_data = (void*)pe->u.temp_entry->key;
    p_mask = (void*)pe->u.temp_entry->mask;

    switch (pKey->type)
    {
        case CTC_FIELD_KEY_PORT:
            CTC_PTR_VALID_CHECK(pKey->ext_data);
            p_port = (ctc_field_port_t*)(pKey->ext_data);
            if (is_add)
            {
                if (CTC_FIELD_PORT_TYPE_LOGIC_PORT == p_port->type)
                {
                    CTC_MAX_VALUE_CHECK(p_port->logic_port, SYS_USW_SCL_LOGIC_PORT_MAX_NUM);
                    SetDsUserIdVlanPortDscpHashKey(V, isLogicPort_f, p_data, 1);
                    SetDsUserIdVlanPortDscpHashKey(V, isLabel_f, p_data, 0);
                    SetDsUserIdVlanPortDscpHashKey(V, globalSrcPort_f, p_data, p_port->logic_port);
                }
                else if (CTC_FIELD_PORT_TYPE_PORT_CLASS == p_port->type)
                {
                    SYS_USW_CLASS_ID_RANGE_CHECK(p_port->port_class_id);
                    SetDsUserIdVlanPortDscpHashKey(V, isLabel_f, p_data, 1);
                    SetDsUserIdVlanPortDscpHashKey(V, isLogicPort_f, p_data, 0);
                    SetDsUserIdVlanPortDscpHashKey(V, globalSrcPort_f, p_data, p_port->port_class_id);
                }
                else if (CTC_FIELD_PORT_TYPE_GPORT == p_port->type)
                {
                    if(!SYS_USW_SCL_GPORT_IS_LOCAL(lchip,p_port->gport))
                    {
                        SYS_SCL_DBG_OUT(CTC_DEBUG_LEVEL_ERROR, " Chip is not local! \n");
                        return CTC_E_INVALID_CHIP_ID;
                    }
                    SYS_GLOBAL_PORT_CHECK(p_port->gport);
                    SetDsUserIdVlanPortDscpHashKey(V, isLabel_f, p_data, 0);
                    SetDsUserIdVlanPortDscpHashKey(V, isLogicPort_f, p_data, 0);
                    SetDsUserIdVlanPortDscpHashKey(V, globalSrcPort_f, p_data, SYS_MAP_CTC_GPORT_TO_DRV_GPORT(p_port->gport));
                }
                else
                {
                    SYS_SCL_DBG_OUT(CTC_DEBUG_LEVEL_ERROR, " API or some feature is not supported \n");
                    return CTC_E_NOT_SUPPORT;
                }
                SetDsUserIdVlanPortDscpHashKey(V, isLogicPort_f, p_mask, 1);
                SetDsUserIdVlanPortDscpHashKey(V, isLabel_f, p_mask, 1);
                SetDsUserIdVlanPortDscpHashKey(V, globalSrcPort_f, p_mask, 0xFFFF);
                CTC_BMP_UNSET(pe->u.temp_entry->hash_sel_bmp, DsUserIdVlanPortDscpHashKey_isLogicPort_f);
                CTC_BMP_UNSET(pe->u.temp_entry->hash_sel_bmp, DsUserIdVlanPortDscpHashKey_isLabel_f);
                CTC_BMP_UNSET(pe->u.temp_entry->hash_sel_bmp, DsUserIdVlanPortDscpHashKey_globalSrcPort_f);
            }
            break;

        case CTC_FIELD_KEY_IP_DSCP:
            CTC_MAX_VALUE_CHECK(pKey->data, 0x3F);
            SetDsUserIdVlanPortDscpHashKey(V, dscp_f, p_data, pKey->data);
            SetDsUserIdVlanPortDscpHashKey(V, dscpValid_f, p_data, 1);
            SetDsUserIdVlanPortDscpHashKey(V, dscp_f, p_mask, pKey->mask);
            SetDsUserIdVlanPortDscpHashKey(V, dscpValid_f, p_mask, 1);
            CTC_BMP_UNSET(pe->u.temp_entry->hash_sel_bmp, DsUserIdVlanPortDscpHashKey_dscp_f);
            CTC_BMP_UNSET(pe->u.temp_entry->hash_sel_bmp, DsUserIdVlanPortDscpHashKey_dscpValid_f);
            break;
        case CTC_FIELD_KEY_SVLAN_ID:
            SYS_SCL_VLAN_ID_CHECK(pKey->data);
            SetDsUserIdVlanPortDscpHashKey(V, svlanId_f, p_data, pKey->data);
            SetDsUserIdVlanPortDscpHashKey(V, svlanId_f, p_mask, pKey->mask);
            CTC_BMP_UNSET(pe->u.temp_entry->hash_sel_bmp, DsUserIdVlanPortDscpHashKey_svlanId_f);
            break;
        case CTC_FIELD_KEY_HASH_VALID:
            SetDsUserIdVlanPortDscpHashKey(V, valid_f, p_data, 1);
            CTC_BMP_UNSET(pe->u.temp_entry->hash_sel_bmp, DsUserIdVlanPortDscpHashKey_valid_f);
            break;
        case SYS_SCL_FIELD_KEY_COMMON:
            SetDsUserIdVlanPortDscpHashKey(V, hashType_f, p_data, DRV_ENUM(DRV_USERIDHASHTYPE_VLANDSCPPORT));
            SetDsUserIdVlanPortDscpHashKey(V, hashType_f, p_mask, 0xFF);
            CTC_BMP_UNSET(pe->u.temp_entry->hash_sel_bmp, DsUserIdVlanPortDscpHashKey_hashType_f);
            CTC_BMP_UNSET(pe->u.temp_entry->hash_sel_bmp, DsUserIdVlanPortDscpHashKey_dsAdIndex_f);
            break;
        case SYS_SCL_FIELD_KEY_AD_INDEX:
            SetDsUserIdVlanPortDscpHashKey(V, dsAdIndex_f, p_data, pKey->data);
            break;
        default:
            SYS_SCL_DBG_OUT(CTC_DEBUG_LEVEL_ERROR, " API or some feature is not supported \n");
            return CTC_E_NOT_SUPPORT;
    }

    return CTC_E_NONE;
}

int32
sys_tmm_scl_build_field_action_userid_vlan_edit(uint8 lchip, void* ds, void* pe_info, ctc_scl_field_action_t* pAction, uint8 is_add)
{
    ctc_scl_vlan_edit_t* p_vlan_edit = NULL;
    sys_scl_sw_entry_t* pe = (sys_scl_sw_entry_t*)pe_info;
    uint8  vlan_edit_valid = 0;
    uint8  do_nothing = 0;
    uint16 profile_id = 0;
    uint32* temp_ds = NULL;
    void* ds_userid = ds;
    ctc_scl_vlan_edit_t vlan_edit_new;

    /*---------------------------------------------------------------*/
    /*update DB (vlan profile)*/

    if (is_add) /*Add or update vlan edit */
    {
        CTC_PTR_VALID_CHECK(pAction->ext_data);
        p_vlan_edit = (ctc_scl_vlan_edit_t*)(pAction->ext_data);

        if (0xFF != p_vlan_edit->tpid_index)
        {
            CTC_MAX_VALUE_CHECK(p_vlan_edit->tpid_index, 3);
        }
        CTC_ERROR_RETURN(sys_usw_scl_check_vlan_edit(lchip, p_vlan_edit, &do_nothing));
        if (pe->u.temp_entry->temp_ad.vlan_edit)
        {
            SYS_SCL_DBG_OUT(CTC_DEBUG_LEVEL_INFO, "Remove vlan profile :%d\n", pe->u.temp_entry->temp_ad.vlan_edit->profile_id);
        }

       /*Add/Update new vlan edit*/
        pe->u.temp_entry->temp_ad.vlan_edit = sys_usw_scl_add_vlan_edit_action_profile(lchip, p_vlan_edit, (void*)pe->u.temp_entry->temp_ad.vlan_edit);

        if (!pe->u.temp_entry->temp_ad.vlan_edit)
        {
            SYS_SCL_DBG_OUT(CTC_DEBUG_LEVEL_ERROR, " No resource in ASIC \n");
            CTC_ERROR_RETURN(CTC_E_NO_RESOURCE);
        }

        SYS_SCL_DBG_OUT(CTC_DEBUG_LEVEL_INFO, "Add new vlan profile :%d\n", pe->u.temp_entry->temp_ad.vlan_edit->profile_id);

        /*vlan edit valid*/
        profile_id = pe->u.temp_entry->temp_ad.vlan_edit->profile_id;
        vlan_edit_valid = 1;
    }
    else   /*Remove or Recovery vlan edit */
    {
        /*Remove vlan edit*/
        if (!pe->u.temp_entry->temp_ad.vlan_edit)
        {
            CTC_ERROR_RETURN(CTC_E_NOT_EXIST);
        }

        SYS_SCL_DBG_OUT(CTC_DEBUG_LEVEL_INFO, "Remove vlan profile :%d\n", pe->u.temp_entry->temp_ad.vlan_edit->profile_id);

        sal_memset(&vlan_edit_new, 0, sizeof(ctc_scl_vlan_edit_t));

        sys_usw_scl_unmapping_vlan_edit(lchip, &vlan_edit_new, &pe->u.temp_entry->temp_ad.vlan_edit->action_profile);
        p_vlan_edit = &vlan_edit_new;
        sys_usw_scl_remove_vlan_edit_action_profile(lchip, pe->u.temp_entry->temp_ad.vlan_edit);
        pe->u.temp_entry->temp_ad.vlan_edit = NULL;
        /*vlan edit valid*/
        vlan_edit_valid = 0;
    }

    /*---------------------------------------------------------------*/
    /*update DB (temp buffer)*/
    temp_ds = SYS_SCL_TEMP_USERID(ds_userid, SYS_SCL_USERID_BMP_VLAN_XLATE);
    if (vlan_edit_valid)
    {
        /* refer to ctc_vlan_tag_sl_t, only CTC_VLAN_TAG_SL_NEW need to write hw table */
        if (CTC_VLAN_TAG_SL_NEW == p_vlan_edit->ccfi_sl)
        {
            SetTempDsVlanXlate(V, userCcfi_f, temp_ds, p_vlan_edit->ccfi_new);
        }
        if (CTC_VLAN_TAG_SL_NEW == p_vlan_edit->ccos_sl)
        {
            SetTempDsVlanXlate(V, userCcos_f, temp_ds, p_vlan_edit->ccos_new);
        }
        if (CTC_VLAN_TAG_SL_NEW == p_vlan_edit->cvid_sl)
        {
            SetTempDsVlanXlate(V, userCvlanId_f, temp_ds, p_vlan_edit->cvid_new);
        }
        if (CTC_VLAN_TAG_SL_NEW == p_vlan_edit->scfi_sl)
        {
            SetTempDsVlanXlate(V, userScfi_f, temp_ds, p_vlan_edit->scfi_new);
        }
        if (CTC_VLAN_TAG_SL_NEW == p_vlan_edit->scos_sl)
        {
            SetTempDsVlanXlate(V, userScos_f, temp_ds, p_vlan_edit->scos_new);
        }
        if (CTC_VLAN_TAG_SL_NEW == p_vlan_edit->svid_sl)
        {
            SetTempDsVlanXlate(V, userSvlanId_f, temp_ds, p_vlan_edit->svid_new);
        }
    }
    else
    {
        SetTempDsVlanXlate(V, userCcfi_f, temp_ds, 0);
        SetTempDsVlanXlate(V, userCcos_f, temp_ds, 0);
        SetTempDsVlanXlate(V, userCvlanId_f, temp_ds, 0);
        SetTempDsVlanXlate(V, userScfi_f, temp_ds, 0);
        SetTempDsVlanXlate(V, userScos_f, temp_ds, 0);
        SetTempDsVlanXlate(V, userSvlanId_f, temp_ds, 0);
    }
    SetTempDsVlanXlate(V, vlanActionProfileId_f, temp_ds, is_add? profile_id: 0);
    SetTempDsVlanXlate(V, vlanActionProfileValid_f, temp_ds, is_add? 1: 0);
    SetTempDsVlanXlate(V, svlanTagOperationValid_f, temp_ds, is_add? (p_vlan_edit->stag_op? 1: 0): 0);
    SetTempDsVlanXlate(V, cvlanTagOperationValid_f, temp_ds, is_add? (p_vlan_edit->ctag_op? 1: 0): 0);
    return CTC_E_NONE;
}

/*1.get field value; 2.clear field in ds*/
STATIC int32
_sys_tmm_scl_get_old_action_field(  uint8 lchip,
                                    uint8* p_u1_type,
                                    uint8* p_u2_type,
                                    uint8* p_u3_type,
                                    uint8* p_fwd_u_type,
                                    uint32* p_field_value,
                                    void* ds,
                                    sys_scl_sw_entry_t* pe)
{
    uint8  u1_type = pe->u.temp_entry->temp_ad.com.u1_type;
    uint8  u2_type = pe->u.temp_entry->temp_ad.com.u2_type;
    uint8  u3_type = pe->u.temp_entry->temp_ad.com.u3_type;
    uint8  fwd_u_type = *p_fwd_u_type;
    uint8  acl_use_outer = 0;
    uint8  acl_use_outer_valid = 0;
    uint8  ipfix_use_outer = 0;
    uint8  ipfix_use_outer_valid = 0;
    uint8  force_bridge = 0;
    uint8  force_learning = 0;
    uint8  force_route = 0;
    uint16 vrfid = 0;
    uint8 vrfid_valid = 0;
    uint32 random_log = 0;
    uint16 metadata = 0;
    uint8 metadata_valid = 0;
    uint32 chunk_bmp = 0;

    void* temp_ds = NULL;
    uint8 no_aset = 1;

    /*field 1 acl_use_outer*/
    if (pe->u.temp_entry->temp_ad.com.u3_type == SYS_AD_UNION_G_2 && CTC_BMP_ISSET(pe->action_bmp, CTC_SCL_FIELD_ACTION_TYPE_FLOW_LKUP_BY_OUTER_HEAD))
    {
        acl_use_outer = GetDsUserId(V, u3_g2_aclQosUseOuterInfo_f, ds);
        acl_use_outer_valid = GetDsUserId(V, u3_g2_aclQosUseOuterInfoValid_f, ds);
        SetDsUserId(V, u3_g2_aclQosUseOuterInfo_f, ds, 0);
        SetDsUserId(V, u3_g2_aclQosUseOuterInfoValid_f, ds, 0);
        SYS_SET_UNION_TYPE(u3_type, SYS_AD_UNION_G_2, DsUserId, 3, ds, FALSE);
        SetDsUserId(V, u3Type_f, ds, u3_type == SYS_AD_UNION_G_2? 1: 0);
    }
    else if (pe->u.temp_entry->temp_ad.com.u1_type == SYS_AD_UNION_G_1 && CTC_BMP_ISSET(pe->action_bmp, CTC_SCL_FIELD_ACTION_TYPE_FLOW_LKUP_BY_OUTER_HEAD))
    {
        acl_use_outer = GetDsUserId(V, u1_g1_aclQosUseOuterInfo_f, ds);
        acl_use_outer_valid = GetDsUserId(V, u1_g1_aclQosUseOuterInfoValid_f, ds);
        SetDsUserId(V, u1_g1_aclQosUseOuterInfo_f, ds, 0);
        SetDsUserId(V, u1_g1_aclQosUseOuterInfoValid_f, ds, 0);
        SYS_SET_UNION_TYPE(u1_type, SYS_AD_UNION_G_1, DsUserId, 1, ds, FALSE);
    }
    p_field_value[1] = acl_use_outer;
    CTC_BIT_SET(p_field_value[0], acl_use_outer_valid? 1: 0);
    /*field 2 vrfid*/
    temp_ds = SYS_SCL_TEMP_USERID(ds, SYS_SCL_USERID_BMP_FWD);
    if (pe->u.temp_entry->temp_ad.com.fwd_bmp == 1 || pe->u.temp_entry->temp_ad.com.fwd_bmp == 5)
    {
        vrfid = GetTempDsFwdInfo(V, u_g4_fid_f, temp_ds);
        vrfid_valid = GetTempDsFwdInfo(V, u_g4_vrfIdValid_f, temp_ds);
        SetTempDsFwdInfo(V, u_g4_fid_f, temp_ds, 0);
        SetTempDsFwdInfo(V, u_g4_vrfIdValid_f, temp_ds, 0);
        SYS_SET_UNION_TYPE(fwd_u_type, SYS_AD_UNION_G_4, TempDsFwdInfo, , temp_ds, FALSE);
        SetTempDsFwdInfo(V, uType_f, temp_ds, fwd_u_type==SYS_AD_UNION_G_4? 3: 0);
    }
    else if (pe->u.temp_entry->temp_ad.com.fwd_bmp == 3)
    {
        vrfid = GetTempDsFwdInfo(V, u2_g1_dsFwdPtr_f, temp_ds);
        vrfid_valid = GetTempDsFwdInfo(V, u2_g1_vrfIdValid_f, temp_ds);
        SetTempDsFwdInfo(V, u2_g1_dsFwdPtr_f, temp_ds, 0);
        SetTempDsFwdInfo(V, u2_g1_vrfIdValid_f, temp_ds, 0);
        SYS_SET_UN_TYPE_HW(SYS_AD_UNION_G_1, TempDsFwdInfo, 2, temp_ds, FALSE);
    }
    p_field_value[2] = vrfid;
    CTC_BIT_SET(p_field_value[0], vrfid_valid ? 2: 0);
    /*field 3 ipfix_use_outer*/
    if (pe->u.temp_entry->temp_ad.com.u3_type == SYS_AD_UNION_G_2 && CTC_BMP_ISSET(pe->action_bmp, CTC_SCL_FIELD_ACTION_TYPE_IPFIX_LKUP_BY_OUTER_HEAD))
    {
        ipfix_use_outer = GetDsUserId(V, u3_g2_ipfixUseOuterInfo_f, ds);
        ipfix_use_outer_valid = GetDsUserId(V, u3_g2_ipfixUseOuterInfoValid_f, ds);
        SetDsUserId(V, u3_g2_ipfixUseOuterInfo_f, ds, 0);
        SetDsUserId(V, u3_g2_ipfixUseOuterInfoValid_f, ds, 0);
        SYS_SET_UNION_TYPE(u3_type, SYS_AD_UNION_G_2, DsUserId, 3, ds, FALSE);
        SetDsUserId(V, u3Type_f, ds, u3_type == SYS_AD_UNION_G_2? 1: 0);
    }
    else if (pe->u.temp_entry->temp_ad.com.u1_type == SYS_AD_UNION_G_1 && CTC_BMP_ISSET(pe->action_bmp, CTC_SCL_FIELD_ACTION_TYPE_IPFIX_LKUP_BY_OUTER_HEAD))
    {
        ipfix_use_outer = GetDsUserId(V, u1_g1_ipfixUseOuterInfo_f, ds);
        ipfix_use_outer_valid = GetDsUserId(V, u1_g1_ipfixUseOuterInfoValid_f, ds);
        SetDsUserId(V, u1_g1_ipfixUseOuterInfo_f, ds, 0);
        SetDsUserId(V, u1_g1_ipfixUseOuterInfoValid_f, ds, 0);
        SYS_SET_UNION_TYPE(u1_type, SYS_AD_UNION_G_1, DsUserId, 1, ds, FALSE);
    }
    p_field_value[3] = ipfix_use_outer;
    CTC_BIT_SET(p_field_value[0], ipfix_use_outer_valid?3:0);
    /*field 4 random_log*/
    if (pe->u.temp_entry->temp_ad.com.u3_type == SYS_AD_UNION_G_2 && CTC_BMP_ISSET(pe->action_bmp, CTC_SCL_FIELD_ACTION_TYPE_RANDOM_LOG))
    {
        random_log = (GetDsUserId(V, u3_g2_aclLogLevel_f, ds)<<24)|
                     (GetDsUserId(V, u3_g2_aclLogId_f, ds)<<16)|
                     (GetDsUserId(V, u3_g2_randomThresholdShift_f, ds));
        SetDsUserId(V, u3_g2_aclLogLevel_f, ds, 0);
        SetDsUserId(V, u3_g2_aclLogId_f, ds, 0);
        SetDsUserId(V, u3_g2_randomThresholdShift_f, ds, 0);
        SYS_SET_UNION_TYPE(u3_type, SYS_AD_UNION_G_2, DsUserId, 3, ds, FALSE);
        SetDsUserId(V, u3Type_f, ds, u3_type == SYS_AD_UNION_G_2? 1: 0);
    }
    else if (pe->u.temp_entry->temp_ad.com.u2_type == SYS_AD_UNION_G_4 && CTC_BMP_ISSET(pe->action_bmp, CTC_SCL_FIELD_ACTION_TYPE_RANDOM_LOG))
    {
        random_log = (GetDsUserId(V, u2_g4_aclLogLevel_f, ds)<<24)|
                     (GetDsUserId(V, u2_g4_aclLogId_f, ds)<<16)|
                     (GetDsUserId(V, u2_g4_randomThresholdShift_f, ds));
        SetDsUserId(V, u2_g4_aclLogLevel_f, ds, 0);
        SetDsUserId(V, u2_g4_aclLogId_f, ds, 0);
        SetDsUserId(V, u2_g4_randomThresholdShift_f, ds, 0);
        SYS_SET_UNION_TYPE(u2_type, SYS_AD_UNION_G_4, DsUserId, 2, ds, FALSE);
        SetDsUserId(V, u2Type_f, ds, u2_type == SYS_AD_UNION_G_4? 3: 0);
    }
    p_field_value[4] = random_log;
    /*field 5 force_bridge*/
    if (pe->u.temp_entry->temp_ad.com.u3_type == SYS_AD_UNION_G_2 && CTC_BMP_ISSET(pe->action_bmp, CTC_SCL_FIELD_ACTION_TYPE_FORCE_BRIDGE))
    {
        force_bridge = GetDsUserId(V, u3_g2_forceBridge_f, ds);
        SetDsUserId(V, u3_g2_forceBridge_f, ds, 0);
        SYS_SET_UNION_TYPE(u3_type, SYS_AD_UNION_G_2, DsUserId, 3, ds, FALSE);
        SetDsUserId(V, u3Type_f, ds, u3_type == SYS_AD_UNION_G_2? 1: 0);
    }
    else if (pe->u.temp_entry->temp_ad.com.u1_type == SYS_AD_UNION_G_1 && CTC_BMP_ISSET(pe->action_bmp, CTC_SCL_FIELD_ACTION_TYPE_FORCE_BRIDGE))
    {
        force_bridge = GetDsUserId(V, u1_g1_forceBridge_f, ds);
        SetDsUserId(V, u1_g1_forceBridge_f, ds, 0);
        SYS_SET_UNION_TYPE(u1_type, SYS_AD_UNION_G_1, DsUserId, 1, ds, FALSE);
        SetDsUserId(V, u1Type_f, ds, 0);
    }
    p_field_value[5] = force_bridge;
    /*field 6 force_learning*/
    if (pe->u.temp_entry->temp_ad.com.u3_type == SYS_AD_UNION_G_2 && CTC_BMP_ISSET(pe->action_bmp, CTC_SCL_FIELD_ACTION_TYPE_FORCE_LEARNING))
    {
        force_learning = GetDsUserId(V, u3_g2_forceLearning_f, ds);
        SetDsUserId(V, u3_g2_forceLearning_f, ds, 0);
        SYS_SET_UNION_TYPE(u3_type, SYS_AD_UNION_G_2, DsUserId, 3, ds, FALSE);
        SetDsUserId(V, u3Type_f, ds, u3_type == SYS_AD_UNION_G_2? 1: 0);
    }
    else if (pe->u.temp_entry->temp_ad.com.u1_type == SYS_AD_UNION_G_1 && CTC_BMP_ISSET(pe->action_bmp, CTC_SCL_FIELD_ACTION_TYPE_FORCE_LEARNING))
    {
        force_learning = GetDsUserId(V, u1_g1_forceLearning_f, ds);
        SetDsUserId(V, u1_g1_forceLearning_f, ds, 0);
        SYS_SET_UNION_TYPE(u1_type, SYS_AD_UNION_G_1, DsUserId, 1, ds, FALSE);
        SetDsUserId(V, u1Type_f, ds, 0);
    }
    p_field_value[6] = force_learning;
    /*field 7 force_route*/
    if (pe->u.temp_entry->temp_ad.com.u3_type == SYS_AD_UNION_G_2 && CTC_BMP_ISSET(pe->action_bmp, CTC_SCL_FIELD_ACTION_TYPE_FORCE_ROUTE))
    {
        force_route = GetDsUserId(V, u3_g2_forceRoute_f, ds);
        SetDsUserId(V, u3_g2_forceRoute_f, ds, 0);
        SYS_SET_UNION_TYPE(u3_type, SYS_AD_UNION_G_2, DsUserId, 3, ds, FALSE);
        SetDsUserId(V, u3Type_f, ds, u3_type == SYS_AD_UNION_G_2? 1: 0);
    }
    else if (pe->u.temp_entry->temp_ad.com.u1_type == SYS_AD_UNION_G_1 && CTC_BMP_ISSET(pe->action_bmp, CTC_SCL_FIELD_ACTION_TYPE_FORCE_ROUTE))
    {
        force_route = GetDsUserId(V, u1_g1_forceRoute_f, ds);
        SetDsUserId(V, u1_g1_forceRoute_f, ds, 0);
        SYS_SET_UNION_TYPE(u1_type, SYS_AD_UNION_G_1, DsUserId, 1, ds, FALSE);
        SetDsUserId(V, u1Type_f, ds, 0);
    }
    p_field_value[7] = force_route;

    /*field 8 metadata, only AT support*/
     if(DRV_FROM_AT(lchip) && CTC_BMP_ISSET(pe->action_bmp, CTC_SCL_FIELD_ACTION_TYPE_METADATA))
     {
           _sys_usw_scl_check_xdata(lchip, pe, NULL,pe->u.temp_entry->action, 0, &chunk_bmp);
     }
     
     if(DRV_FROM_AT(lchip) && CTC_BMP_ISSET(pe->action_bmp, CTC_SCL_FIELD_ACTION_TYPE_METADATA) && (pe->u.temp_entry->temp_ad.com.u2_type == SYS_AD_UNION_G_2)
         && !(CTC_BMP_ISSET(pe->action_bmp, CTC_SCL_FIELD_ACTION_TYPE_SRC_CID) || CTC_BMP_ISSET(pe->action_bmp, CTC_SCL_FIELD_ACTION_TYPE_DST_CID) ||
         (CTC_BMP_ISSET(pe->action_bmp, CTC_SCL_FIELD_ACTION_TYPE_XDATA) && 
         (CTC_FLAG_ISSET(chunk_bmp, SYS_SCL_XDATA_IGS_CHUNK2_BYTE0) || CTC_FLAG_ISSET(chunk_bmp, SYS_SCL_XDATA_IGS_CHUNK2_BYTE1)))))
    {
        metadata= GetDsUserId(V, u2_g2_categoryId_f, ds)&0x7FFF;
        metadata_valid = GetDsUserId(V, u2_g2_metadataTypeExt_f, ds);

        SetDsUserId(V, u2_g2_categoryId_f , ds, 0);
        SetDsUserId(V, u2_g2_categoryType_f , ds, 0);
        SetDsUserId(V, u2_g2_metadataTypeExt_f , ds, 0);
        SetDsUserId(V, u2_g2_categoryIdValid_f, ds, 0);
        SetDsUserId(V, u2_g2_xAdDataValid_f, ds, 0);
        
        SYS_SET_UNION_TYPE(u2_type, SYS_AD_UNION_G_2, DsUserId, 2, ds, FALSE);
        SetDsUserId(V, u2Type_f, ds, 0);
    }
    else if(DRV_FROM_AT(lchip) && CTC_BMP_ISSET(pe->action_bmp, CTC_SCL_FIELD_ACTION_TYPE_METADATA) && (pe->u.temp_entry->temp_ad.com.u1_type == SYS_AD_UNION_G_1))
    {
        metadata = GetDsUserId(V, u1_g1_metadata_f, ds);
        metadata_valid = GetDsUserId(V, u1_g1_metadataTypeExt_f, ds) && (pe->u.temp_entry->temp_ad.com.u1_type == SYS_AD_UNION_G_1);

        SetDsUserId(V, u1_g1_metadata_f, ds, 0);
        SetDsUserId(V, u1_g1_metadataTypeExt_f, ds, 0);
        SetDsUserId(V, u1_g1_metadataType_f, ds, 0);
        SYS_SET_UNION_TYPE(u1_type, SYS_AD_UNION_G_1, DsUserId, 1, ds, FALSE);
        SetDsUserId(V, u1Type_f, ds, 0);
    }
    p_field_value[8] = metadata;
    CTC_BIT_SET(p_field_value[0], metadata_valid ? 8:0);

    *p_u1_type = u1_type;
    *p_u2_type = u2_type;
    *p_u3_type = u3_type;
    *p_fwd_u_type = fwd_u_type;
    return CTC_E_NONE;
}

/*set field in ds*/
STATIC int32
_sys_tmm_scl_set_new_action_field(  uint8 lchip,
                                    uint8 is_add,
                                    uint8 fwd_bmp,
                                    uint8* p_u1_type,
                                    uint8* p_u2_type,
                                    uint8* p_u3_type,
                                    uint8* p_fwd_u_type,
                                    uint8* p_userid_bmp,
                                    uint32* p_field_value,
                                    void* ds,
                                    sys_scl_sw_entry_t* pe,
                                    ctc_scl_field_action_t* pAction)
{
    uint8  u1_type = *p_u1_type;
    uint8  u2_type = *p_u2_type;
    uint8  u3_type = *p_u3_type;
    uint8  fwd_u_type = *p_fwd_u_type;
    uint8  userid_bmp = *p_userid_bmp;
    uint8  acl_use_outer = p_field_value[1];
    uint16 vrfid = p_field_value[2];
    uint8  ipfix_use_outer = p_field_value[3];
    uint32 random_log = p_field_value[4];
    uint8  force_bridge = p_field_value[5];
    uint8  force_learning = p_field_value[6];
    uint8  force_route = p_field_value[7];
    uint16  metadata =  p_field_value[8];
    uint32 chunk_bmp = 0;
    uint8  no_aset =  1;
    uint8  acl_use_outer_valid = ((CTC_IS_BIT_SET(p_field_value[0], 1)  && (pAction->type != CTC_SCL_FIELD_ACTION_TYPE_FLOW_LKUP_BY_OUTER_HEAD)) ||
                                    (is_add && pAction->type == CTC_SCL_FIELD_ACTION_TYPE_FLOW_LKUP_BY_OUTER_HEAD));
    uint8  vrfid_valid = ((CTC_IS_BIT_SET(p_field_value[0], 2) && (pAction->type != CTC_SCL_FIELD_ACTION_TYPE_VRFID)) ||
                            (is_add && pAction->type == CTC_SCL_FIELD_ACTION_TYPE_VRFID));
    uint8  ipfix_use_outer_valid = ((CTC_IS_BIT_SET(p_field_value[0], 3) && (pAction->type != CTC_SCL_FIELD_ACTION_TYPE_IPFIX_LKUP_BY_OUTER_HEAD)) ||
                                      (is_add && pAction->type == CTC_SCL_FIELD_ACTION_TYPE_IPFIX_LKUP_BY_OUTER_HEAD));
    uint8  random_log_valid = ( (random_log && (pAction->type != CTC_SCL_FIELD_ACTION_TYPE_RANDOM_LOG)) ||
                                (is_add && pAction->type == CTC_SCL_FIELD_ACTION_TYPE_RANDOM_LOG));
    uint8  force_bridge_valid = (  (force_bridge && (pAction->type != CTC_SCL_FIELD_ACTION_TYPE_FORCE_BRIDGE)) ||
                                    (is_add && pAction->type == CTC_SCL_FIELD_ACTION_TYPE_FORCE_BRIDGE));
    uint8  force_learning_valid = (  (force_learning && (pAction->type != CTC_SCL_FIELD_ACTION_TYPE_FORCE_LEARNING)) ||
                                    (is_add && pAction->type == CTC_SCL_FIELD_ACTION_TYPE_FORCE_LEARNING));
    uint8  force_route_valid = (  (force_route && (pAction->type != CTC_SCL_FIELD_ACTION_TYPE_FORCE_ROUTE)) ||
                                    (is_add && pAction->type == CTC_SCL_FIELD_ACTION_TYPE_FORCE_ROUTE));

    uint8  metadata_valid = ((CTC_IS_BIT_SET(p_field_value[0], 8) && (pAction->type != CTC_SCL_FIELD_ACTION_TYPE_METADATA)) || 
                                (is_add && pAction->type == CTC_SCL_FIELD_ACTION_TYPE_METADATA));

    void* temp_ds = NULL;

    /*chk acl_use_outer/ipfix_use_outer/force_bridge/force_learning/force_route*/
    if (SYS_SCL_CHK_UNION(u3_type, SYS_AD_UNION_G_2) &&
        SYS_SCL_CHK_UNION(u1_type, SYS_AD_UNION_G_1))
    {
        SYS_SCL_DBG_OUT(CTC_DEBUG_LEVEL_ERROR, "  Both u3 and u1 are used! Line: %u \n", __LINE__);
        return CTC_E_PARAM_CONFLICT;
    }

    /*set acl_use_outer*/
    if (!SYS_SCL_CHK_UNION(u3_type, SYS_AD_UNION_G_2) && acl_use_outer_valid)  /*g2 valid*/
    {
        SetDsUserId(V, u3_g2_aclQosUseOuterInfo_f, ds, acl_use_outer);
        SetDsUserId(V, u3_g2_aclQosUseOuterInfoValid_f, ds, 1);
        SYS_SET_UNION_TYPE(u3_type, SYS_AD_UNION_G_2, DsUserId, 3, ds, TRUE);
        SetDsUserId(V, u3Type_f, ds, 1);
        SYS_SCL_BIT_SET(userid_bmp, SYS_SCL_USERID_BMP_U1_G1, ds, FALSE);
    }
    else if (acl_use_outer_valid)
    {
        SetDsUserId(V, u1_g1_aclQosUseOuterInfo_f, ds, acl_use_outer);
        SetDsUserId(V, u1_g1_aclQosUseOuterInfoValid_f, ds, 1);
        SYS_SET_UNION_TYPE(u1_type, SYS_AD_UNION_G_1, DsUserId, 1, ds, TRUE);
        SetDsUserId(V, u1Type_f, ds, 0);
        SYS_SCL_BIT_SET(userid_bmp, SYS_SCL_USERID_BMP_U1_G1, ds, TRUE);
    }

    /*chk vrfid*/
    temp_ds = SYS_SCL_TEMP_USERID(ds, SYS_SCL_USERID_BMP_FWD);
    if (fwd_bmp == 7 &&
        CTC_IS_BIT_SET(pe->u.temp_entry->temp_ad.com.fwd_bmp, 0))
    {
        SYS_SCL_DBG_OUT(CTC_DEBUG_LEVEL_ERROR, "  Both u2 and u are used! Line: %u \n", __LINE__);
        return CTC_E_PARAM_CONFLICT;
    }

    /*set vrfid*/
    if ((fwd_bmp == 1 || fwd_bmp == 5) && vrfid_valid)   /*use fid*/
    {
        SYS_CHECK_UNION_BITMAP(fwd_u_type, SYS_AD_UNION_G_4);
        SetTempDsFwdInfo(V, u_g4_fid_f, temp_ds, vrfid);
        SetTempDsFwdInfo(V, u_g4_vrfIdValid_f, temp_ds, 1);
        SYS_SET_UNION_TYPE(fwd_u_type, SYS_AD_UNION_G_4, TempDsFwdInfo, , temp_ds, TRUE);
        SetTempDsFwdInfo(V, uType_f, temp_ds, 3);
    }
    else if ((fwd_bmp == 3) && vrfid_valid)  /*use fwd*/
    {
        SYS_CHK_UN_BMP_HW(SYS_AD_UNION_G_1, TempDsFwdInfo, 2, temp_ds);
        SetTempDsFwdInfo(V, u2_g1_dsFwdPtr_f, temp_ds, vrfid);
        SetTempDsFwdInfo(V, u2_g1_vrfIdValid_f, temp_ds, 1);
        SYS_SET_UN_TYPE_HW(SYS_AD_UNION_G_1, TempDsFwdInfo, 2, temp_ds, TRUE);
    }

    /*set ipfix_use_outer*/
    if (!SYS_SCL_CHK_UNION(u3_type, SYS_AD_UNION_G_2) && ipfix_use_outer_valid)  /*g2 valid*/
    {
        SetDsUserId(V, u3_g2_ipfixUseOuterInfo_f, ds, ipfix_use_outer);
        SetDsUserId(V, u3_g2_ipfixUseOuterInfoValid_f, ds, 1);
        SYS_SET_UNION_TYPE(u3_type, SYS_AD_UNION_G_2, DsUserId, 3, ds, TRUE);
        SYS_SCL_BIT_SET(userid_bmp, SYS_SCL_USERID_BMP_U1_G1, ds, FALSE);
        SetDsUserId(V, u3Type_f, ds, 1);
    }
    else if (ipfix_use_outer_valid)
    {
        SetDsUserId(V, u1_g1_ipfixUseOuterInfo_f, ds, ipfix_use_outer);
        SetDsUserId(V, u1_g1_ipfixUseOuterInfoValid_f, ds, 1);
        SYS_SET_UNION_TYPE(u1_type, SYS_AD_UNION_G_1, DsUserId, 1, ds, TRUE);
        SYS_SCL_BIT_SET(userid_bmp, SYS_SCL_USERID_BMP_U1_G1, ds, TRUE);
        SetDsUserId(V, u1Type_f, ds, 0);
    }
    /*chk random_log*/
    if (SYS_SCL_CHK_UNION(u3_type, SYS_AD_UNION_G_2) &&
        SYS_SCL_CHK_UNION(u2_type, SYS_AD_UNION_G_4) && random_log_valid)
    {
        SYS_SCL_DBG_OUT(CTC_DEBUG_LEVEL_ERROR, "  Both u3 and u2 are used! Line: %u \n", __LINE__);
        return CTC_E_PARAM_CONFLICT;
    }
    /*set random_log*/
    if (!SYS_SCL_CHK_UNION(u3_type, SYS_AD_UNION_G_2) && random_log_valid)  /*g2 valid*/
    {
        SetDsUserId(V, u3_g2_aclLogLevel_f, ds, random_log>>24);
        SetDsUserId(V, u3_g2_aclLogId_f, ds, (random_log>>16)&0xFF);
        SetDsUserId(V, u3_g2_randomThresholdShift_f, ds, random_log & 0xFFFF);
        SYS_SET_UNION_TYPE(u3_type, SYS_AD_UNION_G_2, DsUserId, 3, ds, TRUE);
        SYS_SCL_BIT_SET(userid_bmp, SYS_SCL_USERID_BMP_U1_G1, ds, FALSE);
        SetDsUserId(V, u3Type_f, ds, 1);
    }
    else if (random_log_valid)
    {
        SetDsUserId(V, u2_g4_aclLogLevel_f, ds, random_log>>24);
        SetDsUserId(V, u2_g4_aclLogId_f, ds, (random_log>>16)&0xFF);
        SetDsUserId(V, u2_g4_randomThresholdShift_f, ds, random_log & 0xFFFF);
        SYS_SET_UNION_TYPE(u2_type, SYS_AD_UNION_G_4, DsUserId, 2, ds, TRUE);
        SYS_SCL_BIT_SET(userid_bmp, SYS_SCL_USERID_BMP_U1_G1, ds, TRUE);
        SetDsUserId(V, u2Type_f, ds, 3);
    }
    /*set force_bridge*/
    if (!SYS_SCL_CHK_UNION(u3_type, SYS_AD_UNION_G_2) && force_bridge_valid)  /*g2 valid*/
    {
        SetDsUserId(V, u3_g2_forceBridge_f, ds, force_bridge);
        SYS_SET_UNION_TYPE(u3_type, SYS_AD_UNION_G_2, DsUserId, 3, ds, TRUE);
        SYS_SCL_BIT_SET(userid_bmp, SYS_SCL_USERID_BMP_U1_G1, ds, FALSE);
        SetDsUserId(V, u3Type_f, ds, 1);
    }
    else if (force_bridge_valid)
    {
        SetDsUserId(V, u1_g1_forceBridge_f, ds, force_bridge);
        SYS_SET_UNION_TYPE(u1_type, SYS_AD_UNION_G_1, DsUserId, 1, ds, TRUE);
        SYS_SCL_BIT_SET(userid_bmp, SYS_SCL_USERID_BMP_U1_G1, ds, TRUE);
        SetDsUserId(V, u1Type_f, ds, 0);
    }
    /*set force_learning*/
    if (!SYS_SCL_CHK_UNION(u3_type, SYS_AD_UNION_G_2) && force_learning_valid)  /*g2 valid*/
    {
        SetDsUserId(V, u3_g2_forceLearning_f, ds, force_learning);
        SYS_SET_UNION_TYPE(u3_type, SYS_AD_UNION_G_2, DsUserId, 3, ds, TRUE);
        SYS_SCL_BIT_SET(userid_bmp, SYS_SCL_USERID_BMP_U1_G1, ds, FALSE);
        SetDsUserId(V, u3Type_f, ds, 1);
    }
    else if (force_learning_valid)
    {
        SetDsUserId(V, u1_g1_forceLearning_f, ds, force_learning);
        SYS_SET_UNION_TYPE(u1_type, SYS_AD_UNION_G_1, DsUserId, 1, ds, TRUE);
        SYS_SCL_BIT_SET(userid_bmp, SYS_SCL_USERID_BMP_U1_G1, ds, TRUE);
        SetDsUserId(V, u1Type_f, ds, 0);
    }
    /*set force_route*/
    if (!SYS_SCL_CHK_UNION(u3_type, SYS_AD_UNION_G_2) && force_route_valid)  /*g2 valid*/
    {
        SetDsUserId(V, u3_g2_forceRoute_f, ds, force_route);
        SYS_SET_UNION_TYPE(u3_type, SYS_AD_UNION_G_2, DsUserId, 3, ds, TRUE);
        SYS_SCL_BIT_SET(userid_bmp, SYS_SCL_USERID_BMP_U1_G1, ds, FALSE);
        SetDsUserId(V, u3Type_f, ds, 1);
    }
    else if (force_route_valid)
    {
        SetDsUserId(V, u1_g1_forceRoute_f, ds, force_route);
        SYS_SET_UNION_TYPE(u1_type, SYS_AD_UNION_G_1, DsUserId, 1, ds, TRUE);
        SYS_SCL_BIT_SET(userid_bmp, SYS_SCL_USERID_BMP_U1_G1, ds, TRUE);
        SetDsUserId(V, u1Type_f, ds, 0);
    }
    
    /* set metadata */
    if(DRV_FROM_AT(lchip) && metadata_valid)
    {
        _sys_usw_scl_check_xdata(lchip, pe, pAction,ds,0, &chunk_bmp);
         /*chk metadata*/
        if ((SYS_SCL_CHK_UNION(u1_type, SYS_AD_UNION_G_1) || CTC_FLAG_ISSET(chunk_bmp, SYS_SCL_XDATA_IGS_CHUNK1_NIBBLE3_0)) &&
            (SYS_SCL_CHK_UNION(u2_type, SYS_AD_UNION_G_2) || (CTC_FLAG_ISSET(chunk_bmp, SYS_SCL_XDATA_IGS_CHUNK2_BYTE0) || CTC_FLAG_ISSET(chunk_bmp, SYS_SCL_XDATA_IGS_CHUNK2_BYTE1))))
        {
            SYS_SCL_DBG_OUT(CTC_DEBUG_LEVEL_ERROR, "  Both u1 and u2 are used! Line: %u \n", __LINE__);
            return CTC_E_PARAM_CONFLICT;
        }
    }
        
    if(DRV_FROM_AT(lchip)  && metadata_valid && !SYS_SCL_CHK_UNION(u2_type , SYS_AD_UNION_G_2) &&
        !((pAction->type == CTC_SCL_FIELD_ACTION_TYPE_SRC_CID) || (pAction->type == CTC_SCL_FIELD_ACTION_TYPE_DST_CID) ||
            CTC_BMP_ISSET(pe->action_bmp, CTC_SCL_FIELD_ACTION_TYPE_SRC_CID) || CTC_BMP_ISSET(pe->action_bmp, CTC_SCL_FIELD_ACTION_TYPE_DST_CID) ||
            CTC_FLAG_ISSET(chunk_bmp, SYS_SCL_XDATA_IGS_CHUNK2_BYTE0) || CTC_FLAG_ISSET(chunk_bmp, SYS_SCL_XDATA_IGS_CHUNK2_BYTE1)))
    {
        metadata |= CTC_METADATA_TYPE_METADATA << 15;
        SetDsUserId(V, u2_g2_categoryId_f, ds, metadata);
        SetDsUserId(V, u2_g2_metadataTypeExt_f, ds,  1);
        SetDsUserId(V, u2_g2_categoryType_f, ds,  0);
        SetDsUserId(V, u2_g2_categoryIdValid_f, ds, 0);
        SetDsUserId(V, u2_g2_xAdDataValid_f, ds, 0);

        SYS_SET_UNION_TYPE(u2_type, SYS_AD_UNION_G_2, DsUserId, 2, ds, TRUE);
        SYS_SCL_BIT_SET(userid_bmp, SYS_SCL_USERID_BMP_U1_G1, ds, FALSE);
        
        SetDsUserId(V, u2Type_f, ds, 1);
    }
    else if(DRV_FROM_AT(lchip) && metadata_valid)
    {
        SetDsUserId(V, u1_g1_metadataTypeExt_f, ds, 1);
        SetDsUserId(V, u1_g1_metadataType_f, ds,  CTC_METADATA_TYPE_METADATA);
        SetDsUserId(V, u1_g1_metadata_f, ds,  metadata);
        SetDsUserId(V, u1Type_f, ds, 0);

        SYS_SCL_BIT_SET(userid_bmp, SYS_SCL_USERID_BMP_U1_G1, ds, TRUE);
        SYS_SET_UNION_TYPE(u1_type, SYS_AD_UNION_G_1, DsUserId, 1, ds, TRUE);
    }

    /* userid_bmp changed, need check conflict */
    if (is_add && ( \
       (userid_bmp<=0x17 && userid_bmp>=0x13) || (userid_bmp<=0x1F && userid_bmp>=0x1B) || \
       (userid_bmp<=0x27 && userid_bmp>=0x24) || (userid_bmp<=0x3F && userid_bmp>=0x2A) || \
       (userid_bmp<=0x4F && userid_bmp>=0x4D) || (userid_bmp<=0x57 && userid_bmp>=0x51) || \
       (userid_bmp<=0x5F && userid_bmp>=0x59) || (userid_bmp<=0x7F && userid_bmp>=0x62) || \
       (userid_bmp==0x0F) || (userid_bmp==0x47) || (userid_bmp==0x4B) ))
    {
        SYS_SCL_DBG_OUT(CTC_DEBUG_LEVEL_ERROR, " %% SCL # userid_bitmap: 0x%X\n", userid_bmp);
        CTC_ERROR_RETURN(CTC_E_NOT_SUPPORT);
    }

    SYS_SCL_DBG_OUT(CTC_DEBUG_LEVEL_INFO, "  Add acl use outer :%u \n", acl_use_outer);
    SYS_SCL_DBG_OUT(CTC_DEBUG_LEVEL_INFO, "  Add vrfid         :%u \n", vrfid);
    SYS_SCL_DBG_OUT(CTC_DEBUG_LEVEL_INFO, "  Add acl use outer :%u \n", ipfix_use_outer);
    SYS_SCL_DBG_OUT(CTC_DEBUG_LEVEL_INFO, "  Add random log    :%u \n", random_log);
    SYS_SCL_DBG_OUT(CTC_DEBUG_LEVEL_INFO, "  Add force bridge  :%u \n", force_bridge);
    SYS_SCL_DBG_OUT(CTC_DEBUG_LEVEL_INFO, "  Add force learning:%u \n", force_learning);
    SYS_SCL_DBG_OUT(CTC_DEBUG_LEVEL_INFO, "  Add force route   :%u \n", force_route);
    SYS_SCL_DBG_OUT(CTC_DEBUG_LEVEL_INFO, "  Add metadata :%u \n", metadata);

    *p_u1_type = u1_type;
    *p_u2_type = u2_type;
    *p_u3_type = u3_type;
    *p_fwd_u_type = fwd_u_type;
    *p_userid_bmp = userid_bmp;
    return CTC_E_NONE;
}

int32
sys_tmm_scl_build_field_action_userid(uint8 lchip, ctc_scl_field_action_t* pAction, void* pe_info, uint8 is_add)
{
    sys_scl_sw_entry_t* pe = (sys_scl_sw_entry_t*)pe_info;
    sys_nh_info_dsnh_t nhinfo;
    uint32 temp_data = 0;
    uint32 field_buffer[9] = {0};
    uint32 nexthop_id  = 0;
    sys_qos_policer_param_t policer_param;
    void* ds_userid = NULL;
    uint8   gchip = 0;
    uint8   have_dsfwd = 0;
    uint8   binding_mac_sa = 0;
    uint8   is_to_cpu = 0;
    uint8   is_discard = 0;
    uint8   userid_bmp = pe->u.temp_entry->temp_ad.com.userid_bmp;
    uint8   fwd_u_type = pe->u.temp_entry->temp_ad.com.u4_type;
    uint8   logic_u_type = pe->u.temp_entry->temp_ad.com.u5_type;
    uint8   fwd_bmp = pe->u.temp_entry->temp_ad.com.fwd_bmp;
    uint8   u3_type = pe->u.temp_entry->temp_ad.com.u3_type;
    uint8   u2_type = pe->u.temp_entry->temp_ad.com.u2_type;
    uint8   u1_type = pe->u.temp_entry->temp_ad.com.u1_type;
    ctc_scl_field_action_t  field_action;
    ctc_scl_logic_port_t* p_logic_port = NULL;
    ctc_scl_aps_t* aps = NULL;
    ctc_scl_qos_map_t* p_qos = NULL;
    ctc_scl_bind_t* bind = NULL;
    sys_scl_dot1br_t* p_dot1br = NULL;
    hw_mac_addr_t mac = {0};
    uint16 old_logic_port = 0;
    uint16 fid = 0;
    uint32* temp_ds = NULL;
    uint32 bind_data[2] = {0};
    ctc_scl_force_decap_t* p_decap = NULL;
    ctc_scl_snooping_parser_t* p_snooping_parser = NULL;
    sys_stats_param_t statsid;
    ds_t    temp_ds_userid;
    ctc_security_hmac_t hmac;
    uint8 no_aset = 1;
    
    CTC_PTR_VALID_CHECK(pAction);
    CTC_PTR_VALID_CHECK(pe->u.temp_entry);

    if (is_add)     /*Add new action, must remove old action first, when old action is conflict with new action*/
    {
        CTC_ERROR_RETURN(_sys_usw_scl_remove_old_action(lchip, pAction, pe, CTC_SCL_FIELD_ACTION_TYPE_REDIRECT, CTC_SCL_FIELD_ACTION_TYPE_DISCARD));
        CTC_ERROR_RETURN(_sys_usw_scl_remove_old_action(lchip, pAction, pe, CTC_SCL_FIELD_ACTION_TYPE_REDIRECT_PORT, CTC_SCL_FIELD_ACTION_TYPE_DISCARD));
        CTC_ERROR_RETURN(_sys_usw_scl_remove_old_action(lchip, pAction, pe, CTC_SCL_FIELD_ACTION_TYPE_DISCARD, CTC_SCL_FIELD_ACTION_TYPE_REDIRECT));
        CTC_ERROR_RETURN(_sys_usw_scl_remove_old_action(lchip, pAction, pe, CTC_SCL_FIELD_ACTION_TYPE_DISCARD, CTC_SCL_FIELD_ACTION_TYPE_REDIRECT_PORT));
    }

    sal_memset(&nhinfo, 0, sizeof(sys_nh_info_dsnh_t));
    sal_memset(&policer_param, 0, sizeof(sys_qos_policer_param_t));
    sal_memset(&field_action, 0, sizeof(ctc_scl_field_action_t));
    sal_memcpy(temp_ds_userid, pe->u.temp_entry->action, sizeof(pe->u.temp_entry->action));

    ds_userid = (void*)temp_ds_userid;

    if (is_add)
    {
        CTC_ERROR_RETURN(_sys_tmm_scl_map_action_field_to_userid_bmp(lchip, pAction, pe, ds_userid, &userid_bmp, TRUE));
    }

    switch(pAction->type)
    {
        case CTC_SCL_FIELD_ACTION_TYPE_REDIRECT:
        case CTC_SCL_FIELD_ACTION_TYPE_REDIRECT_PORT:
        case CTC_SCL_FIELD_ACTION_TYPE_DISCARD:
            CTC_BIT_SET(fwd_bmp, 2);
            break;
        case CTC_SCL_FIELD_ACTION_TYPE_FID:
            CTC_BIT_SET(fwd_bmp, 1);
            break;
        case CTC_SCL_FIELD_ACTION_TYPE_VRFID:
            CTC_BIT_SET(fwd_bmp, 0);
            break;
        default :
            break;
    }
    if (fwd_bmp==7)
    {
        SYS_SCL_DBG_OUT(CTC_DEBUG_LEVEL_ERROR, "  Redirect/discard, fid and vrfid can't be used together! Line: %u \n", __LINE__);
        return CTC_E_PARAM_CONFLICT;
    }
    
    sys_tmm_scl_move_dsuserid_to_temp(lchip, ds_userid, pe->u.temp_entry->temp_ad.com.userid_bmp);

    temp_ds = SYS_SCL_TEMP_USERID(ds_userid, SYS_SCL_USERID_BMP_LOGIC_PORT);
    old_logic_port = GetTempDsLogicPort(V, logicSrcPort_f, temp_ds);

    _sys_tmm_scl_get_old_action_field(lchip, &u1_type, &u2_type, &u3_type, &fwd_u_type, field_buffer, ds_userid, pe);

    switch (pAction->type)
    {
        case SYS_SCL_FIELD_ACTION_TYPE_ACTION_COMMON:
            SetDsUserId(V, adType_f, ds_userid, 0);
            break;
        case SYS_SCL_FIELD_ACTION_TYPE_IS_HALF:
            SetDsUserId(V, isHalf_f, ds_userid, is_add? 1: 0);
            break;
        case CTC_SCL_FIELD_ACTION_TYPE_PENDING:
        case CTC_SCL_FIELD_ACTION_TYPE_CANCEL_ALL:
             return _sys_usw_scl_build_field_action_igs_cancel_all(lchip, pAction, pe, is_add);
         case CTC_SCL_FIELD_ACTION_TYPE_DISCARD:
            if (SYS_SCL_ACTION_FLOW == pe->action_type)
            {
                temp_ds = SYS_SCL_TEMP_USERID(ds_userid, SYS_SCL_USERID_BMP_FLOW);
                SetTempDsFlow(V, discard_f, temp_ds, is_add? 1: 0);
                pe->u.temp_entry->temp_ad.fwd_type = is_add ? SYS_SCL_FWD_DISCARD : 0;
                break;
            }
            temp_ds = SYS_SCL_TEMP_USERID(ds_userid, SYS_SCL_USERID_BMP_FWD);
            SYS_USW_SCL_REMOVE_ACTION_CHK(is_add, pe, pAction, SYS_SCL_FWD_REDIRECT, CTC_SCL_FIELD_ACTION_TYPE_DISCARD);
            SYS_USW_SCL_REMOVE_ACTION_CHK(is_add, pe, pAction, SYS_SCL_FWD_REDIRECT_PORT, CTC_SCL_FIELD_ACTION_TYPE_DISCARD);
            if (pe->u.temp_entry->temp_ad.bind_nh && is_add)
            {
                /*already use merge dsfwd*/
                sal_memset(temp_ds, 0, 2 * sizeof(uint32));
                _sys_usw_scl_unbind_nexthop(lchip, pe, pe->u.temp_entry->temp_ad.nexthop_id);
            }
            else
            {
                SYS_CHK_UN_BMP_HW(SYS_AD_UNION_G_1, TempDsFwdInfo, 2, temp_ds);
            }
            SetTempDsFwdInfo(V, u2_g1_dsFwdPtr_f, temp_ds, is_add? 0xFFFF: 0);
            SetTempDsFwdInfo(V, u2Type_f, temp_ds, 0);
            pe->u.temp_entry->temp_ad.fwd_type = is_add ? SYS_SCL_FWD_DISCARD : 0;
            break;
        case CTC_SCL_FIELD_ACTION_TYPE_LOGIC_PORT:
            if(is_add)
            {
                p_logic_port =  (ctc_scl_logic_port_t*) pAction->ext_data;
                CTC_PTR_VALID_CHECK(pAction->ext_data);
                CTC_MAX_VALUE_CHECK(p_logic_port->logic_port, MCHIP_CAP(SYS_CAP_MAX_LOGIC_PORT));
                CTC_MAX_VALUE_CHECK(p_logic_port->logic_port_type, 1);
            }
            if(pe->u.temp_entry->temp_ad.service_id && DRV_IS_TMM(lchip))
            {
                if (is_add)
                {
                    CTC_ERROR_RETURN(sys_usw_qos_bind_service_logic_srcport(lchip, pe->u.temp_entry->temp_ad.service_id,p_logic_port->logic_port));
                    if(old_logic_port && old_logic_port != p_logic_port->logic_port )
                    {
                        sys_usw_qos_unbind_service_logic_srcport(lchip, pe->u.temp_entry->temp_ad.service_id,old_logic_port);
                    }
                }
                else
                {
                    CTC_ERROR_RETURN(sys_usw_qos_unbind_service_logic_srcport(lchip, pe->u.temp_entry->temp_ad.service_id,old_logic_port));
                }
            }
            temp_ds = SYS_SCL_TEMP_USERID(ds_userid, SYS_SCL_USERID_BMP_LOGIC_PORT);
            SetTempDsLogicPort(V, logicSrcPort_f, temp_ds, is_add? p_logic_port->logic_port: 0);
            SetTempDsLogicPort(V, logicSrcPortType_f, temp_ds, is_add? p_logic_port->logic_port_type: 0);
            SetTempDsLogicPort(V, logicSrcPortBindingCheck_f, temp_ds, is_add? p_logic_port->binding_en: 0);
            break;
        case CTC_SCL_FIELD_ACTION_TYPE_LOGIC_PORT_TYPE:
            temp_ds = SYS_SCL_TEMP_USERID(ds_userid, SYS_SCL_USERID_BMP_LOGIC_PORT);
            SetTempDsLogicPort(V, logicSrcPortType_f, temp_ds, is_add? 1: 0);
            break;
        case CTC_SCL_FIELD_ACTION_TYPE_STP_ID:
            CTC_MAX_VALUE_CHECK(pAction->data0, 127);
            SetDsUserId(V, u1_g1_stpId_f, ds_userid, is_add? pAction->data0: 0);
            SetDsUserId(V, u1_g1_stpIdValid_f, ds_userid, is_add? 1: 0);
            SYS_SET_UNION_TYPE(u1_type, SYS_AD_UNION_G_1, DsUserId, 1, ds_userid, is_add);
            break;
        case CTC_SCL_FIELD_ACTION_TYPE_APS:
            aps = pAction->ext_data;
            temp_ds = SYS_SCL_TEMP_USERID(ds_userid, SYS_SCL_USERID_BMP_LOGIC_PORT);
            if (is_add)
            {
                CTC_PTR_VALID_CHECK(aps);
                SYS_TMM_SCL_UPDATE_DSFWD();
                SYS_CHECK_UNION_BITMAP(fwd_u_type, SYS_AD_UNION_G_1);
                aps = pAction->ext_data;
                SYS_APS_GROUP_ID_CHECK(aps->aps_select_group_id);
                CTC_MAX_VALUE_CHECK(aps->is_working_path, 1);
                if (aps->protected_vlan_valid)
                {
                    CTC_VLAN_RANGE_CHECK(aps->protected_vlan);
                    SetTempDsLogicPort(V, vsiIdValid_f, temp_ds, 0);
                    SetTempDsLogicPort(V, vsiIdOrUserVlanPtr_f, temp_ds, (1<<14) + aps->protected_vlan);
                }
            }
            else
            {
                SetTempDsLogicPort(V, vsiIdOrUserVlanPtr_f, temp_ds, 0);
            }
            temp_ds = SYS_SCL_TEMP_USERID(ds_userid, SYS_SCL_USERID_BMP_FWD);
            SetTempDsFwdInfo(V, u_g1_apsSelectValid_f, temp_ds, is_add? 1: 0);
            SetTempDsFwdInfo(V, u_g1_apsSelectProtectingPath_f, temp_ds, is_add? (!aps->is_working_path): 0);
            SetTempDsFwdInfo(V, u_g1_apsSelectGroupId_f, temp_ds, is_add? aps->aps_select_group_id: 0);
            SYS_SET_UNION_TYPE(fwd_u_type, SYS_AD_UNION_G_1, TempDsFwdInfo, , temp_ds, is_add);
            SetTempDsFwdInfo(V, uType_f, temp_ds, 0);
            break;
        case CTC_SCL_FIELD_ACTION_TYPE_REDIRECT_PORT:
            SYS_USW_SCL_REMOVE_ACTION_CHK(is_add, pe, pAction, SYS_SCL_FWD_DISCARD, CTC_SCL_FIELD_ACTION_TYPE_REDIRECT_PORT)
            SYS_USW_SCL_REMOVE_ACTION_CHK(is_add, pe, pAction, SYS_SCL_FWD_REDIRECT, CTC_SCL_FIELD_ACTION_TYPE_REDIRECT_PORT)
            if (is_add)
            {
                uint8 type = 0;
                type = pAction->data1 ? CTC_NH_PARAM_BRGUC_SUB_TYPE_BASIC : CTC_NH_PARAM_BRGUC_SUB_TYPE_BYPASS;
                SYS_GLOBAL_PORT_CHECK(pAction->data0);
                CTC_ERROR_RETURN(sys_usw_l2_get_ucast_nh(lchip, pAction->data0, type, &nexthop_id));
            }

             /*do not need break, continue to CTC_ACL_FIELD_ACTION_REDIRECT*/
        case CTC_SCL_FIELD_ACTION_TYPE_REDIRECT:
            SYS_USW_SCL_REMOVE_ACTION_CHK(is_add, pe, pAction, SYS_SCL_FWD_REDIRECT_PORT, CTC_SCL_FIELD_ACTION_TYPE_REDIRECT)
            SYS_USW_SCL_REMOVE_ACTION_CHK(is_add, pe, pAction, SYS_SCL_FWD_DISCARD, CTC_SCL_FIELD_ACTION_TYPE_REDIRECT)
            /* data0: nexthopid */
            nexthop_id = is_add ? ((CTC_SCL_FIELD_ACTION_TYPE_REDIRECT_PORT != pAction->type) ? pAction->data0 : nexthop_id): pe->u.temp_entry->temp_ad.nexthop_id;
            temp_ds = SYS_SCL_TEMP_USERID(ds_userid, SYS_SCL_USERID_BMP_FWD);
            no_aset = 1; //fwd_u_type cann't defined by redirect action
            if (is_add)
            {
                CTC_ERROR_RETURN(sys_usw_nh_get_nhinfo(lchip, nexthop_id, &nhinfo, 0));
                if (pe->u.temp_entry->temp_ad.nexthop_id)
                {
                    if (fwd_u_type==SYS_AD_UNION_G_3)
                    {
                        SetTempDsFwdInfo(V, u2_g2_adDestMap_f, temp_ds, 0);
                        SetTempDsFwdInfo(V, u2_g2_adApsBridgeEn_f, temp_ds, 0);
                        SetTempDsFwdInfo(V, u2_g2_bypassIngressEdit_f, temp_ds, 0);
                        SetTempDsFwdInfo(V, u2Type_f, temp_ds, 0);
                        SetTempDsFwdInfo(V, u_g3_adNextHopExt_f, temp_ds, 0);
                        SetTempDsFwdInfo(V, u_g3_adNextHopPtr_f, temp_ds, 0);
                        SetTempDsFwdInfo(V, uType_f, temp_ds, 0);
                        fwd_u_type = SYS_AD_UNION_G_NA;
                    }
                    else if (fwd_u_type==SYS_AD_UNION_G_2 && !GetTempDsFwdInfo(V, u_g2_advMacsecEnable_f, temp_ds))
                    {
                        SetTempDsFwdInfo(V, u_g2_ecmpGroupId_f, temp_ds, 0);
                        SetTempDsFwdInfo(V, u_g2_advMacsecEnable_f, temp_ds, 0);
                        SetTempDsFwdInfo(V, uType_f, temp_ds, 0);
                        fwd_u_type = SYS_AD_UNION_G_NA;
                    }
                    else
                    {
                        SetTempDsFwdInfo(V, u2_g1_dsFwdPtr_f, temp_ds, 0);
                    }
                 
                    CTC_BMP_UNSET(pe->action_bmp, CTC_SCL_FIELD_ACTION_TYPE_REDIRECT_PORT);
                    CTC_BMP_UNSET(pe->action_bmp, CTC_SCL_FIELD_ACTION_TYPE_REDIRECT);
           
                }
                _sys_usw_scl_unbind_nexthop(lchip, pe, pe->u.temp_entry->temp_ad.nexthop_id);
                have_dsfwd = ( fwd_u_type == SYS_AD_UNION_G_2) || nhinfo.dsfwd_valid || pe->is_default || nhinfo.cloud_sec_en || (nhinfo.merge_dsfwd ==2);
                if(!have_dsfwd && !nhinfo.ecmp_valid)
                {
                    have_dsfwd |= (CTC_E_NONE != _sys_usw_scl_bind_nexthop(lchip, pe, nexthop_id));
                    have_dsfwd |= (fwd_u_type != SYS_AD_UNION_G_3) && (fwd_u_type != SYS_AD_UNION_G_NA);
                }
                /* for scl ecmp */
                if (nhinfo.ecmp_valid)
                {
                    SYS_CHECK_UNION_BITMAP(fwd_u_type, SYS_AD_UNION_G_2);
                    if(GetTempDsFwdInfo(V, u_g2_advMacsecEnable_f, temp_ds))
                    {
                        return CTC_E_PARAM_CONFLICT;
                    }
                    SetTempDsFwdInfo(V, u_g2_ecmpGroupId_f, temp_ds, nhinfo.ecmp_group_id);
                    SetTempDsFwdInfo(V, u_g2_advMacsecEnable_f, temp_ds, 0);
                    SYS_SET_UNION_TYPE(fwd_u_type, SYS_AD_UNION_G_2, TempDsFwdInfo, , temp_ds, is_add);
                    SetTempDsFwdInfo(V, uType_f, temp_ds, 1);
                }
                else if (have_dsfwd)
                {
                    SYS_CHK_UN_BMP_HW(SYS_AD_UNION_G_1, TempDsFwdInfo, 2, temp_ds);
                    CTC_ERROR_RETURN(sys_usw_nh_get_dsfwd_offset(lchip, nexthop_id, &temp_data, 0, CTC_FEATURE_SCL));
                    SetTempDsFwdInfo(V, u2_g1_dsFwdPtr_f, temp_ds, temp_data);
                    SetTempDsFwdInfo(V, u2Type_f, temp_ds, 0);
                }
                else
                {
                    /*merge dsfwd*/
                    SYS_CHK_UN_BMP_HW(SYS_AD_UNION_G_2, TempDsFwdInfo, 2, temp_ds);
                    SYS_CHECK_UNION_BITMAP(fwd_u_type, SYS_AD_UNION_G_3);
                    SetTempDsFwdInfo(V, u2_g2_adDestMap_f, temp_ds, nhinfo.dest_map);
                    SetTempDsFwdInfo(V, u2_g2_adApsBridgeEn_f, temp_ds, nhinfo.aps_en);
                    SetTempDsFwdInfo(V, u2_g2_bypassIngressEdit_f, temp_ds, nhinfo.bypass_igr_edit);
                    SetTempDsFwdInfo(V, u_g3_adNextHopExt_f, temp_ds, nhinfo.nexthop_ext);
                    SetTempDsFwdInfo(V, u_g3_adNextHopPtr_f, temp_ds, nhinfo.dsnh_offset);
                    SYS_SET_UNION_TYPE(fwd_u_type, SYS_AD_UNION_G_3, TempDsFwdInfo, , temp_ds, is_add);
                    SetTempDsFwdInfo(V, u2Type_f, temp_ds, 1);
                    SetTempDsFwdInfo(V, uType_f, temp_ds, 2);
                }
                temp_ds = SYS_SCL_TEMP_USERID(ds_userid, SYS_SCL_USERID_BMP_LOGIC_PORT);
                if (!GetTempDsLogicPort(V, vsiIdOrUserVlanPtr_f, temp_ds) && !GetTempDsLogicPort(V, vsiIdValid_f, temp_ds) && !pAction->data1)
                {
                    SetTempDsLogicPort(V, vsiIdOrUserVlanPtr_f, temp_ds, (1<<14)+MCHIP_CAP(SYS_CAP_SCL_BY_PASS_VLAN_PTR));
                }
                else if(GetTempDsLogicPort(V, vsiIdOrUserVlanPtr_f, temp_ds) == (1<<14)+MCHIP_CAP(SYS_CAP_SCL_BY_PASS_VLAN_PTR) && \
                        !GetTempDsLogicPort(V, vsiIdValid_f, temp_ds) && pAction->data1)
                {
                    SetTempDsLogicPort(V, vsiIdOrUserVlanPtr_f, temp_ds, 0);
                }
                pe->u.temp_entry->temp_ad.nexthop_id = nexthop_id;
            }
            else if(pe->u.temp_entry->temp_ad.nexthop_id)
            {
                if (fwd_u_type == SYS_AD_UNION_G_2 && !GetTempDsFwdInfo(V, u_g2_advMacsecEnable_f, temp_ds))
                {
                    SYS_CHECK_UNION_BITMAP(fwd_u_type, SYS_AD_UNION_G_2);
                    SetTempDsFwdInfo(V, u_g2_ecmpGroupId_f, temp_ds, 0);
                    SYS_SET_UNION_TYPE(fwd_u_type, SYS_AD_UNION_G_2, TempDsFwdInfo, , temp_ds, is_add);
                    SetTempDsFwdInfo(V, uType_f, temp_ds, fwd_u_type == SYS_AD_UNION_G_NA? 0: 1);
                }
                else if (pe->u.temp_entry->temp_ad.bind_nh)
                {
                    /*using merge dsfwd*/
                    SYS_CHK_UN_BMP_HW(SYS_AD_UNION_G_2, TempDsFwdInfo, 2, temp_ds);
                    SYS_CHECK_UNION_BITMAP(fwd_u_type, SYS_AD_UNION_G_3);
                    SetTempDsFwdInfo(V, u2_g2_adDestMap_f, temp_ds, 0);
                    SetTempDsFwdInfo(V, u2_g2_adApsBridgeEn_f, temp_ds, 0);
                    SetTempDsFwdInfo(V, u2_g2_bypassIngressEdit_f, temp_ds, 0);
                    SetTempDsFwdInfo(V, u_g3_adNextHopExt_f, temp_ds, 0);
                    SetTempDsFwdInfo(V, u_g3_adNextHopPtr_f, temp_ds, 0);
                    SYS_SET_UNION_TYPE(fwd_u_type, SYS_AD_UNION_G_3, TempDsFwdInfo, , temp_ds, 0);
                    SYS_SET_UN_TYPE_HW(SYS_AD_UNION_G_2, TempDsFwdInfo, 2, temp_ds, 0);
                    SetTempDsFwdInfo(V, uType_f, temp_ds, (fwd_u_type == SYS_AD_UNION_G_NA)? 0: 2);
                    _sys_usw_scl_unbind_nexthop(lchip, pe, pe->u.temp_entry->temp_ad.nexthop_id);
                }
                else
                {
                    SYS_CHK_UN_BMP_HW(SYS_AD_UNION_G_1, TempDsFwdInfo, 2, temp_ds);
                    SetTempDsFwdInfo(V, u2_g1_dsFwdPtr_f, temp_ds, 0);
                    SetTempDsFwdInfo(V, u2Type_f, temp_ds, 0);
                }
                temp_ds = SYS_SCL_TEMP_USERID(ds_userid, SYS_SCL_USERID_BMP_LOGIC_PORT);
                if ((MCHIP_CAP(SYS_CAP_SCL_BY_PASS_VLAN_PTR) == (0x3FFF & GetTempDsLogicPort(V, vsiIdOrUserVlanPtr_f, temp_ds))) && !GetTempDsLogicPort(V, vsiIdValid_f, temp_ds))
                {
                    SetTempDsLogicPort(V, vsiIdOrUserVlanPtr_f, temp_ds, 0);
                }
                pe->u.temp_entry->temp_ad.nexthop_id = 0;
            }
            SetDsUserId(V, denyBridge_f, ds_userid, is_add? 1: 0);
            pe->u.temp_entry->temp_ad.fwd_type = is_add ? ((CTC_SCL_FIELD_ACTION_TYPE_REDIRECT == pAction->type) ? 
                                        SYS_SCL_FWD_REDIRECT: SYS_SCL_FWD_REDIRECT_PORT): 0;
            break;
        case CTC_SCL_FIELD_ACTION_TYPE_POLICER_ID:
            SYS_CHECK_UNION_BITMAP(u3_type, SYS_AD_UNION_G_1);
            if (is_add)
            {
                CTC_MAX_VALUE_CHECK(pAction->data1, CTC_SCL_PLC_NUM - 1);
                CTC_NOT_ZERO_CHECK(pAction->data0);

                switch(pAction->data1)
                {
                case CTC_SCL_PLC_SVC:
                    policer_param.sys_policer_type = SYS_QOS_POLICER_TYPE_SVC;
                    break;
                case CTC_SCL_PLC_SERVICE:
                default:
                    policer_param.sys_policer_type = SYS_QOS_POLICER_TYPE_SERVICE;
                    break;
                }
                policer_param.policer_id = pAction->data0;
                policer_param.glb_policer = !MCHIP_FEATURE_PP_EN(lchip,CTC_FEATURE_SCL);
                CTC_ERROR_RETURN(sys_usw_qos_policer_index_get(lchip, &policer_param));
                if (policer_param.is_bwp)
                {
                    SetDsUserId(V, policerPhbEn_f, ds_userid, 1);
                }
                SetDsUserId(V, policerLvlSel_f, ds_userid, policer_param.level);
                SetDsUserId(V, policerPtr_f, ds_userid, policer_param.policer_ptr);
            }
            else
            {
                SetDsUserId(V, policerPhbEn_f, ds_userid, 0);
                SetDsUserId(V, policerLvlSel_f, ds_userid, 0);
                SetDsUserId(V, policerPtr_f, ds_userid, 0);
            }
            SYS_SET_UNION_TYPE(u3_type, SYS_AD_UNION_G_1, DsUserId, 3, ds_userid, is_add);
            SetDsUserId(V, u3Type_f, ds_userid, 0); 
            pe->u.temp_entry->temp_ad.is_service_policer = is_add? (pAction->data1 == CTC_SCL_PLC_SERVICE ? 1 : 0) : 0;
            break;
        case CTC_SCL_FIELD_ACTION_TYPE_SERVICE_ID:
            if (is_add)
            {
                CTC_MAX_VALUE_CHECK(pAction->data0, MCHIP_CAP(SYS_CAP_SCL_SERVICE_ID_NUM) - 1);
                CTC_MIN_VALUE_CHECK(pAction->data0, 1);
            }
            SYS_CHECK_UNION_BITMAP(u2_type, SYS_AD_UNION_G_1);
            if(old_logic_port && DRV_IS_TMM(lchip))
            {
                if (is_add)
                {
                    if(pe->u.temp_entry->temp_ad.service_id && (pe->u.temp_entry->temp_ad.service_id != pAction->data0))
                    {
                        sys_usw_qos_unbind_service_logic_srcport(lchip, pe->u.temp_entry->temp_ad.service_id,old_logic_port);
                    }
                    CTC_ERROR_RETURN(sys_usw_qos_bind_service_logic_srcport(lchip, pAction->data0,old_logic_port));
                }
                else
                {
                    CTC_ERROR_RETURN(sys_usw_qos_unbind_service_logic_srcport(lchip, pe->u.temp_entry->temp_ad.service_id,old_logic_port));
                }
            }

            pe->u.temp_entry->temp_ad.service_id = is_add ? pAction->data0 : 0;
            SetDsUserId(V, u2_g1_serviceId_f, ds_userid, is_add? pAction->data0: 0);
            SYS_SET_UNION_TYPE(u2_type, SYS_AD_UNION_G_1, DsUserId, 2, ds_userid, is_add);
            SetDsUserId(V, u2Type_f, ds_userid, 0);
            break;
        case CTC_SCL_FIELD_ACTION_TYPE_STATS:
            sal_memset(&statsid, 0, sizeof(statsid));
            if (is_add)
            {
                statsid.dir = CTC_INGRESS;
                statsid.type = SYS_STATS_TYPE_SCL;
                statsid.id = pAction->data0;
                statsid.acl_pri = pe->group_priority;
                CTC_ERROR_RETURN(sys_usw_flow_stats_alloc_statsptr(lchip, &statsid));
            }
            SetDsUserId(V, statsPtr_f, ds_userid, statsid.ptr & 0xFFFF);
            break;
        case CTC_SCL_FIELD_ACTION_TYPE_SPAN_FLOW:
            SYS_CHECK_UNION_BITMAP(u2_type, SYS_AD_UNION_G_4);
            SetDsUserId(V, u2_g4_isSpanPkt_f, ds_userid, is_add? 1: 0);
            SYS_SET_UNION_TYPE(u2_type, SYS_AD_UNION_G_4, DsUserId, 2, ds_userid, is_add);
            SetDsUserId(V, u2Type_f, ds_userid, (u2_type == SYS_AD_UNION_G_NA)? 0: 3);
            break;
        case CTC_SCL_FIELD_ACTION_TYPE_QOS_MAP:
            temp_ds = SYS_SCL_TEMP_USERID(ds_userid, SYS_SCL_USERID_BMP_LOGIC_PORT);
            /* the param in the Ds to be checked */
            /* when user priority is not equal to zeros, but we just do not need it , this situaition is thought to be reasonable */
            if (is_add)
            {
                p_qos = (ctc_scl_qos_map_t*) (pAction->ext_data);
                CTC_PTR_VALID_CHECK(pAction->ext_data);
                CTC_MAX_VALUE_CHECK(p_qos->priority, 0xF);
                CTC_MAX_VALUE_CHECK(p_qos->color, 0x3);
                CTC_MAX_VALUE_CHECK(p_qos->trust_dscp, 0x1);
                CTC_MAX_VALUE_CHECK(p_qos->dscp_domain, 0xF);
                CTC_MAX_VALUE_CHECK(p_qos->cos_domain, 0x7);
                CTC_MAX_VALUE_CHECK(p_qos->dscp, 0x3F);
                CTC_MAX_VALUE_CHECK(p_qos->trust_cos, 0x1);

                if (CTC_FLAG_ISSET(p_qos->flag, CTC_SCL_QOS_MAP_FLAG_PRIORITY_VALID) || p_qos->color)
                {
                    SYS_CHECK_UNION_BITMAP(logic_u_type, SYS_AD_UNION_G_1);
                    SetTempDsLogicPort(V, uType_f, temp_ds, 0);
                    SetTempDsLogicPort(V, u_g1_userColor_f, temp_ds, p_qos->color);
                    SetTempDsLogicPort(V, u_g1_userPrioValid_f, temp_ds, CTC_FLAG_ISSET(p_qos->flag, CTC_SCL_QOS_MAP_FLAG_PRIORITY_VALID)? 1: 0);
                    SetTempDsLogicPort(V, u_g1_userPrio_f, temp_ds, p_qos->priority);
                    SYS_SET_UNION_TYPE(logic_u_type,SYS_AD_UNION_G_1,TempDsLogicPort,,temp_ds, is_add);
                }
                else
                {
                    SYS_CHECK_UNION_BITMAP(logic_u_type, SYS_AD_UNION_G_2);
                    SetTempDsLogicPort(V, uType_f, temp_ds, 1);
                    SetTempDsLogicPort(V, u_g2_trustDscp_f, temp_ds, p_qos->trust_dscp);
                    SetTempDsLogicPort(V, u_g2_dscpPhbPtr_f, temp_ds, p_qos->dscp_domain);
                    SetTempDsLogicPort(V, u_g2_cosPhbPtr_f, temp_ds, p_qos->cos_domain);
                    if (CTC_FLAG_ISSET(p_qos->flag, CTC_SCL_QOS_MAP_FLAG_TRUST_COS_VALID))
                    {
                        SetTempDsLogicPort(V, u_g2_cosPhbUseInnerValid_f, temp_ds, 1);
                        SetTempDsLogicPort(V, u_g2_cosPhbUseInner_f, temp_ds, p_qos->trust_cos);
                    }
                    SYS_SET_UNION_TYPE(logic_u_type,SYS_AD_UNION_G_2,TempDsLogicPort,,temp_ds, is_add);
                }
                if (CTC_FLAG_ISSET(p_qos->flag, CTC_SCL_QOS_MAP_FLAG_DSCP_VALID))
                {
                    SYS_CHECK_UNION_BITMAP(u2_type, SYS_AD_UNION_G_4);
                    SetDsUserId(V, u2_g4_newDscpValid_f, ds_userid, 1);
                    SetDsUserId(V, u2_g4_newDscp_f, ds_userid, p_qos->dscp);
                    SYS_SET_UNION_TYPE(u2_type, SYS_AD_UNION_G_4, DsUserId, 2, ds_userid, is_add);
                    SetDsUserId(V, u2Type_f, ds_userid, 3);
                }
            }
            else
            {
                if (u2_type == SYS_AD_UNION_G_4 && GetDsUserId(V, u2_g4_newDscpValid_f, ds_userid))
                {
                    SetDsUserId(V, u2_g4_newDscpValid_f, ds_userid, 0);
                    SetDsUserId(V, u2_g4_newDscp_f, ds_userid, 0);
                    SYS_SET_UNION_TYPE(u2_type, SYS_AD_UNION_G_4, DsUserId, 2, ds_userid, 0);
                    SetDsUserId(V, u2Type_f, ds_userid, u2_type == SYS_AD_UNION_G_NA? 0: 3);
                }
                if(logic_u_type == SYS_AD_UNION_G_2)
                {
                    SetTempDsLogicPort(V, u_g2_trustDscp_f, temp_ds, 0);
                    SetTempDsLogicPort(V, u_g2_dscpPhbPtr_f, temp_ds, 0);
                    SetTempDsLogicPort(V, u_g2_cosPhbPtr_f, temp_ds, 0);
                    SetTempDsLogicPort(V, u_g2_cosPhbUseInnerValid_f, temp_ds, 0);
                    SetTempDsLogicPort(V, u_g2_cosPhbUseInner_f, temp_ds, 0);
                }
                else
                {
                    SetTempDsLogicPort(V, u_g1_userColor_f, temp_ds, 0);
                    SetTempDsLogicPort(V, u_g1_userPrioValid_f, temp_ds, 0);
                    SetTempDsLogicPort(V, u_g1_userPrio_f, temp_ds, 0);
                }
                SetTempDsLogicPort(V, uType_f, temp_ds, 0);
                logic_u_type = 0;
            }
            break;
        case CTC_SCL_FIELD_ACTION_TYPE_EFD:
            CTC_MAX_VALUE_CHECK(pAction->data0, 0x3);
            SYS_CHECK_UNION_BITMAP(u3_type, SYS_AD_UNION_G_2);
            SetDsUserId(V, u3_g2_efdAction_f, ds_userid, is_add? pAction->data0: 0);
            SYS_SET_UNION_TYPE(u3_type, SYS_AD_UNION_G_2, DsUserId, 3, ds_userid, is_add);
            SetDsUserId(V, u3Type_f, ds_userid, (u3_type == SYS_AD_UNION_G_NA)? 0: 1);
            break;
        case CTC_SCL_FIELD_ACTION_TYPE_PTP_CLOCK_ID:
            CTC_MAX_VALUE_CHECK(pAction->data0, 0x3);
            SYS_CHECK_UNION_BITMAP(u3_type, SYS_AD_UNION_G_2);
            SetDsUserId(V, u3_g2_ptpIndex_f, ds_userid, is_add? pAction->data0: 0);
            SYS_SET_UNION_TYPE(u3_type, SYS_AD_UNION_G_2, DsUserId, 3, ds_userid, is_add);
            SetDsUserId(V, u3Type_f, ds_userid, (u3_type == SYS_AD_UNION_G_NA)? 0: 1);
            break;
        case CTC_SCL_FIELD_ACTION_TYPE_FLOW_LKUP_BY_OUTER_HEAD:
            if (SYS_SCL_CHK_UNION(u3_type, SYS_AD_UNION_G_2) && SYS_SCL_CHK_UNION(u1_type, SYS_AD_UNION_G_1))
            {
                SYS_SCL_DBG_OUT(CTC_DEBUG_LEVEL_ERROR, "  Both u3 and u1 are used! Line: %u \n", __LINE__);
                return CTC_E_PARAM_CONFLICT;
            }
            CTC_MAX_VALUE_CHECK(pAction->data0, 0x1);
            field_buffer[1] = is_add? pAction->data0: 0;
            break;
        case CTC_SCL_FIELD_ACTION_TYPE_SRC_CID:
            CTC_ERROR_RETURN(no_aset ? _sys_usw_scl_chk_category_id_union(lchip, ds_userid, pAction->type) : CTC_E_NONE);
            SYS_CHECK_UNION_BITMAP(u2_type, SYS_AD_UNION_G_2);
            if (is_add)
            {
                SYS_USW_CID_CHECK(lchip, pAction->data0);
                is_add = pAction->data0? 1: 0;  /*disable cid*/
            }
            SetDsUserId(V, u2_g2_metadataTypeExt_f, ds_userid, 0);
            SetDsUserId(V, u2_g2_categoryType_f, ds_userid, is_add? 1: 0);
            SetDsUserId(V, u2_g2_categoryId_f, ds_userid, is_add? pAction->data0: 0);
            SetDsUserId(V, u2_g2_categoryIdValid_f, ds_userid, is_add? 1: 0);
            SYS_SET_UNION_TYPE(u2_type, SYS_AD_UNION_G_2, DsUserId, 2, ds_userid, is_add);
            SetDsUserId(V, u2Type_f, ds_userid, (u2_type == SYS_AD_UNION_G_NA)? 0: 1);
            break;
        case CTC_SCL_FIELD_ACTION_TYPE_DST_CID:
            CTC_ERROR_RETURN(no_aset ? _sys_usw_scl_chk_category_id_union(lchip, ds_userid, pAction->type) : CTC_E_NONE);
            SYS_CHECK_UNION_BITMAP(u2_type, SYS_AD_UNION_G_2);
            if (is_add)
            {
                SYS_USW_CID_CHECK(lchip, pAction->data0);
                is_add = pAction->data0? 1: 0;  /*disable cid*/
            }
            SetDsUserId(V, u2_g2_metadataTypeExt_f, ds_userid, 0);
            SetDsUserId(V, u2_g2_categoryType_f, ds_userid, 0);
            SetDsUserId(V, u2_g2_categoryId_f, ds_userid, is_add? pAction->data0: 0);
            SetDsUserId(V, u2_g2_categoryIdValid_f, ds_userid, is_add? 1: 0);
            SYS_SET_UNION_TYPE(u2_type, SYS_AD_UNION_G_2, DsUserId, 2, ds_userid, is_add);
            SetDsUserId(V, u2Type_f, ds_userid, (u2_type == SYS_AD_UNION_G_NA)? 0: 1);
            break;
        case CTC_SCL_FIELD_ACTION_TYPE_UDF_ID:
            SYS_CHECK_UNION_BITMAP(u2_type, SYS_AD_UNION_G_1);
            if(is_add)
            {
                sys_acl_udf_info_t udf_info;
                CTC_ERROR_RETURN(sys_usw_acl_get_udf_info(lchip, pAction->data0, &udf_info));
                if(!udf_info.is_sudf) /* service udf must use 512~1023*/
                {
                    return CTC_E_INVALID_PARAM;
                }
                SetDsUserId(V, u2_g1_udfHitIndex_f, ds_userid, udf_info.key_index);
            }
            else
            {
                SetDsUserId(V, u2_g1_udfHitIndex_f, ds_userid, 0);
            }
            SYS_SET_UNION_TYPE(u2_type, SYS_AD_UNION_G_1, DsUserId, 2, ds_userid, is_add);
            SetDsUserId(V, u2Type_f, ds_userid, 0);
            break;
        case CTC_SCL_FIELD_ACTION_TYPE_LOCAL_ARP:
            SYS_CHECK_UNION_BITMAP(u2_type, SYS_AD_UNION_G_4);
            SetDsUserId(V, u2_g4_arpTargetIpIsLocal_f, ds_userid, is_add ? 1 : 0);
            SYS_SET_UNION_TYPE(u2_type, SYS_AD_UNION_G_4, DsUserId, 2, ds_userid, is_add);
            SetDsUserId(V, u2Type_f, ds_userid, u2_type == SYS_AD_UNION_G_4 ? 3 : 0);
            break;
        case CTC_SCL_FIELD_ACTION_TYPE_VLAN_EDIT:
            CTC_ERROR_RETURN(sys_tmm_scl_build_field_action_userid_vlan_edit(lchip, ds_userid, pe, pAction, is_add));
            break;
        case CTC_SCL_FIELD_ACTION_TYPE_FID:
            SYS_TMM_SCL_UPDATE_DSFWD();
            if (CTC_BMP_ISSET(pe->action_bmp, SYS_SCL_FIELD_ACTION_TYPE_VN_ID))
            {
                return CTC_E_PARAM_CONFLICT;
            }
            SYS_CHECK_UNION_BITMAP(fwd_u_type, SYS_AD_UNION_G_4);
            if (pe->u.temp_entry->temp_ad.vpws_oam_en == 1)
            {
                /* for vpws, can not config fid */
                return CTC_E_INVALID_CONFIG;
            }
            temp_ds = SYS_SCL_TEMP_USERID(ds_userid, SYS_SCL_USERID_BMP_FWD);
            CTC_ERROR_RETURN(GetTempDsFwdInfo(V, u_g4_vrfIdValid_f, temp_ds)? CTC_E_PARAM_CONFLICT: CTC_E_NONE);
            /*data0:fid*/
            CTC_MAX_VALUE_CHECK(pAction->data0, 0x7FFF);
            SetTempDsFwdInfo(V, u_g4_vsiIdValid_f, temp_ds, is_add? 1: 0);
            SetTempDsFwdInfo(V, u_g4_fid_f, temp_ds, is_add? pAction->data0: 0);
            SYS_SET_UNION_TYPE(fwd_u_type,SYS_AD_UNION_G_4,TempDsFwdInfo, ,temp_ds, is_add);
            SetTempDsFwdInfo(V, uType_f, temp_ds, (fwd_u_type==SYS_AD_UNION_G_NA)? 0: 3);
            break;
        case CTC_SCL_FIELD_ACTION_TYPE_VRFID:
            /*if (SYS_SCL_CHK_UNION(u3_type, SYS_AD_UNION_G_2) && SYS_SCL_CHK_UNION(u1_type, SYS_AD_UNION_G_1))
            {
                SYS_SCL_DBG_OUT(CTC_DEBUG_LEVEL_ERROR, "  Both u3 and u1 are used! Line: %u \n", __LINE__);
                return CTC_E_PARAM_CONFLICT;
            }*/
            CTC_MAX_VALUE_CHECK(pAction->data0, MCHIP_CAP(SYS_CAP_SPEC_MAX_VRFID));
            field_buffer[2] = is_add? pAction->data0 | (!!pAction->data1 << 13): 0;
            break;
        case SYS_SCL_FIELD_ACTION_TYPE_VN_ID:
            SYS_TMM_SCL_UPDATE_DSFWD();
            if (CTC_BMP_ISSET(pe->action_bmp, CTC_SCL_FIELD_ACTION_TYPE_FID))
            {
                return CTC_E_PARAM_CONFLICT;
            }
            SYS_CHECK_UNION_BITMAP(fwd_u_type, SYS_AD_UNION_G_4);
            /*data0:fid*/
            if (is_add)
            {
                CTC_ERROR_RETURN(sys_usw_vlan_overlay_get_fid(lchip, pAction->data0, &fid));
                CTC_MAX_VALUE_CHECK(fid, 0x3FFF);
            }
            temp_ds = SYS_SCL_TEMP_USERID(ds_userid, SYS_SCL_USERID_BMP_FWD);
            SetTempDsFwdInfo(V, u_g4_vsiIdValid_f, temp_ds, is_add? 1: 0);
            SetTempDsFwdInfo(V, u_g4_fid_f, temp_ds, fid);
            SYS_SET_UNION_TYPE(fwd_u_type,SYS_AD_UNION_G_4,TempDsFwdInfo, ,temp_ds, is_add);
            SetTempDsFwdInfo(V, uType_f, temp_ds, (fwd_u_type==SYS_AD_UNION_G_NA)? 0: 3);          
            break;
        case CTC_SCL_FIELD_ACTION_TYPE_BINDING_EN:
            if (is_add)
            {
                CTC_PTR_VALID_CHECK(pAction->ext_data);
                bind = pAction->ext_data;
                switch (bind->type)
                {
                    case CTC_SCL_BIND_TYPE_PORT:
                        SYS_GLOBAL_PORT_CHECK(bind->gport);
                        bind_data[1] = SYS_MAP_CTC_GPORT_TO_DRV_GPORT(bind->gport);
                        bind_data[0] = 0;
                        break;
                    case CTC_SCL_BIND_TYPE_VLAN:
                        CTC_VLAN_RANGE_CHECK(bind->vlan_id);
                        bind_data[1] = bind->vlan_id << 4;
                        bind_data[0] = 1;
                        break;
                    case CTC_SCL_BIND_TYPE_IPV4SA:
                        bind_data[1] = (bind->ipv4_sa >> 28);
                        bind_data[0] = ((bind->ipv4_sa & 0xFFFFFFF) << 4) | 2;
                        break;
                    case CTC_SCL_BIND_TYPE_IPV4SA_VLAN:
                        CTC_VLAN_RANGE_CHECK(bind->vlan_id);
                        bind_data[1] = (bind->ipv4_sa >> 28) | (bind->vlan_id << 4);
                        bind_data[0] = ((bind->ipv4_sa & 0xFFFFFFF) << 4) | 3;
                        break;
                    case CTC_SCL_BIND_TYPE_MACSA:
                        SYS_USW_SET_HW_MAC(mac, (uint8*)bind->mac_sa);
                        bind_data[0] = mac[0];
                        bind_data[1] = mac[1];
                        binding_mac_sa = 1;
                        break;
                    default:
                        CTC_ERROR_RETURN(CTC_E_INVALID_PARAM);
                }
            }
            temp_ds = SYS_SCL_TEMP_USERID(ds_userid, SYS_SCL_USERID_BMP_BINDING);
            SetTempDsBinding(V, bindingMacSa_f, temp_ds, binding_mac_sa);
            SetTempDsBinding(A, bindingData_f, temp_ds, bind_data);
            break;
        case CTC_SCL_FIELD_ACTION_TYPE_COPY_TO_CPU:
            temp_ds = SYS_SCL_TEMP_USERID(ds_userid, SYS_SCL_USERID_BMP_FLOW);
            SetTempDsFlow(V, exceptionEn_f, temp_ds, is_add? 1: 0);
            break;
        case CTC_SCL_FIELD_ACTION_TYPE_DENY_BRIDGE:
            SetDsUserId(V, denyBridge_f, ds_userid, is_add? 1: 0);
            break;
        case CTC_SCL_FIELD_ACTION_TYPE_OAM:
            if((pAction->data0 == 0 && pe->u.temp_entry->temp_ad.vpws_oam_en) || (pAction->data0 == 1 && !pe->u.temp_entry->temp_ad.vpws_oam_en && GetDsUserId(V, vplsOamEn_f, ds_userid)))
            {
                CTC_ERROR_RETURN(CTC_E_INVALID_CONFIG);
            }
            /* for vpws, check uservlanptr is set */
            temp_ds = SYS_SCL_TEMP_USERID(ds_userid, SYS_SCL_USERID_BMP_LOGIC_PORT);
            /* only redirect can be cover */
            temp_data = !GetTempDsLogicPort(V, vsiIdValid_f, temp_ds)
                        && CTC_IS_BIT_SET(GetTempDsLogicPort(V, vsiIdOrUserVlanPtr_f, temp_ds), 14)
                        && MCHIP_CAP(SYS_CAP_SCL_BY_PASS_VLAN_PTR) != (GetTempDsLogicPort(V, vsiIdOrUserVlanPtr_f, temp_ds) & 0x3FFF);
            temp_ds = SYS_SCL_TEMP_USERID(ds_userid, SYS_SCL_USERID_BMP_FWD);
            if (pAction->data0 == 1 && (temp_data || (3 == GetTempDsFwdInfo(V, uType_f, temp_ds) && GetTempDsFwdInfo(V, u_g4_vrfIdValid_f, temp_ds)))&& !pe->u.temp_entry->temp_ad.vpws_oam_en)
            {/*!pe->u.temp_entry->temp_ad.vpws_oam_en,indiacte CTC_SCL_FIELD_ACTION_TYPE_OAM is not update*/
                CTC_ERROR_RETURN(CTC_E_INVALID_CONFIG);
            }
            if (is_add && (pAction->data0 == 1) && (pAction->data1 > 0xFFF))
            {
                CTC_ERROR_RETURN(CTC_E_INVALID_PARAM);
            }
            SetDsUserId(V, vplsOamEn_f, ds_userid, is_add? 1: 0);
            if (pAction->data0 == 1)
            {
                temp_ds = SYS_SCL_TEMP_USERID(ds_userid, SYS_SCL_USERID_BMP_LOGIC_PORT);
                SetTempDsLogicPort(V, vsiIdOrUserVlanPtr_f, temp_ds, is_add? (pAction->data1 + (1 << 13)) : 0);
                SetTempDsLogicPort(V, vsiIdValid_f, temp_ds, is_add? 1 : 0);
            }
            pe->u.temp_entry->temp_ad.vpws_oam_en = is_add? (pAction->data0 == 1? 1: pe->u.temp_entry->temp_ad.vpws_oam_en): 0;
            break;
        /*
        case CTC_SCL_FIELD_ACTION_TYPE_OAM_TUNNEL_EN:
            SetDsUserId(V, u1_g1_oamTunnelEn_f, ds_userid, is_add? 1: 0);
            SYS_SET_UNION_TYPE(u1_type, SYS_AD_UNION_G_1, DsUserId, 1, ds_userid, is_add);
            break;
        */
        case CTC_SCL_FIELD_ACTION_TYPE_ETREE_LEAF:
            SetDsUserId(V, isLeaf_f, ds_userid, is_add? 1: 0);
            break;
        case CTC_SCL_FIELD_ACTION_TYPE_LOGIC_PORT_SECURITY_EN:
            temp_ds = SYS_SCL_TEMP_USERID(ds_userid, SYS_SCL_USERID_BMP_LOGIC_PORT);
            SetTempDsLogicPort(V, logicPortSecurityEn_f, temp_ds, is_add? 1: 0);
            break;
         case CTC_SCL_FIELD_ACTION_TYPE_MAC_LIMIT :
            is_to_cpu = (CTC_MACLIMIT_ACTION_TOCPU == pAction->data0);
            is_discard = (CTC_MACLIMIT_ACTION_DISCARD == pAction->data0) || is_to_cpu;
            temp_ds = SYS_SCL_TEMP_USERID(ds_userid, SYS_SCL_USERID_BMP_LOGIC_PORT);
            SetTempDsLogicPort(V, logicPortMacSecurityDiscard_f, temp_ds, (is_add? is_discard : 0));
            SetTempDsLogicPort(V, logicPortSecurityExceptionEn_f, temp_ds, (is_add? is_to_cpu : 0));
            break;
        /**< [TM] Set router mac match */
         case CTC_SCL_FIELD_ACTION_TYPE_ROUTER_MAC_MATCH:
            temp_ds = SYS_SCL_TEMP_USERID(ds_userid, SYS_SCL_USERID_BMP_PORT_EXTENDER);
            if (is_add)
            {
                SetDsRouterMacTcamAd(V, isRouterMac_f, &temp_ds[1], is_add? 1: 0);
                CTC_BIT_SET(temp_ds[1], SYS_SCL_USERID_ROUTER_MAC_HIT_BASE);    /*routerMacHit*/
            }
            else
            {
                temp_ds[1] = 0;
            }
            break;
        case SYS_SCL_FIELD_ACTION_TYPE_DOT1BR_PE:
            if (is_add)
            {
                p_dot1br = (sys_scl_dot1br_t*) pAction->ext_data;
                CTC_PTR_VALID_CHECK(pAction->ext_data);
            }
            temp_ds = SYS_SCL_TEMP_USERID(ds_userid, SYS_SCL_USERID_BMP_PORT_EXTENDER);
            SetTempDsPortExtender(V, localPhyPortValid_f, temp_ds, is_add? p_dot1br->lport_valid: 0);
            SetTempDsPortExtender(V, localPhyPort_f, temp_ds, is_add? p_dot1br->lport: 0);
            SetTempDsPortExtender(V, globalSrcPortValid_f, temp_ds, is_add? p_dot1br->src_gport_valid: 0);
            SetTempDsPortExtender(V, globalSrcPort_f, temp_ds, is_add? SYS_MAP_CTC_GPORT_TO_DRV_GPORT(p_dot1br->src_gport): 0);
            SetDsUserId(V, bypassAll_f, ds_userid, is_add? p_dot1br->bypass_all: 0);
            temp_ds = SYS_SCL_TEMP_USERID(ds_userid, SYS_SCL_USERID_BMP_FLOW);
            SetTempDsFlow(V, discard_f, temp_ds, is_add? p_dot1br->src_discard: 0);
            SetTempDsFlow(V, exceptionEn_f, temp_ds, is_add? p_dot1br->exception_en: 0);
            break;
        case CTC_SCL_FIELD_ACTION_TYPE_USER_VLANPTR:
            if (GetDsUserId(V, vplsOamEn_f, ds_userid) && pe->u.temp_entry->temp_ad.vpws_oam_en == 1)
            {
                CTC_ERROR_RETURN(CTC_E_INVALID_CONFIG);
            }
            if (GetTempDsLogicPort(V, vsiIdValid_f, temp_ds))
            {
                CTC_ERROR_RETURN(CTC_E_PARAM_CONFLICT);
            }

            CTC_MAX_VALUE_CHECK(pAction->data0, MCHIP_CAP(SYS_CAP_MAX_VLAN_PTR));
            temp_ds = SYS_SCL_TEMP_USERID(ds_userid, SYS_SCL_USERID_BMP_LOGIC_PORT);
            SetTempDsLogicPort(V, vsiIdOrUserVlanPtr_f, temp_ds, is_add? (pAction->data0+(1<<14)): 0);
            break;
        /*just for get field action use, do nothing*/
        case SYS_SCL_FIELD_ACTION_TYPE_VPLS:
        case SYS_SCL_FIELD_ACTION_TYPE_VPWS:
            break;

        case CTC_SCL_FIELD_ACTION_TYPE_HMAC_ID:
            if (DRV_FROM_AT(lchip))
            {
                return CTC_E_NOT_SUPPORT;
            }
            temp_ds = SYS_SCL_TEMP_USERID(ds_userid, SYS_SCL_USERID_BMP_FWD);
            SYS_CHK_UN_BMP_HW(SYS_AD_UNION_G_2, TempDsFwdInfo, 2, temp_ds);
            SYS_CHECK_UNION_BITMAP(fwd_u_type, SYS_AD_UNION_G_3);
            if (is_add)
            {
                sal_memset(&hmac, 0, sizeof(ctc_security_hmac_t));
                hmac.hmac_id = pAction->data0;
                CTC_ERROR_RETURN(SYS_CB_RET(CTC_E_NOT_SUPPORT, SYS_CB_HMAC_GET_SHA_KEY, lchip, &hmac, &temp_data, 0));
                pAction->data0 = temp_data; /* sha key index */
            }
            sys_usw_get_gchip_id(lchip, &gchip);
            SetTempDsFwdInfo(V, u2_g2_adDestMap_f, temp_ds, is_add? SYS_ENCODE_DESTMAP(gchip, SYS_RSV_PORT_HMAC): 0);
            SetTempDsFwdInfo(V, u2_g2_adApsBridgeEn_f, temp_ds, 0);
            SetTempDsFwdInfo(V, u2_g2_bypassIngressEdit_f, temp_ds, 0);
            SetTempDsFwdInfo(V, u_g3_adNextHopExt_f, temp_ds, 0);
            SetTempDsFwdInfo(V, u_g3_adNextHopPtr_f, temp_ds, is_add? (1<<9): 0);
            SYS_SET_UNION_TYPE(fwd_u_type, SYS_AD_UNION_G_3, TempDsFwdInfo, , temp_ds, is_add);
            SYS_SET_UN_TYPE_HW(SYS_AD_UNION_G_2, TempDsFwdInfo, 2, temp_ds, is_add);
            SetTempDsFwdInfo(V, uType_f, temp_ds, (fwd_u_type==SYS_AD_UNION_G_NA)? 0: 2);
            SetDsUserId(V, denyBridge_f, ds_userid, is_add? 1: 0);
            SetDsUserId(V, denyRoute_f, ds_userid, is_add? 1: 0);
            /* [TMM] no break here, for sha key index use metadata */
        /****** below only flow action ******/
        case CTC_SCL_FIELD_ACTION_TYPE_METADATA:
            SYS_USW_METADATE_CHECK(pAction->data0);
            if (DRV_FROM_AT(lchip))
            {
                field_buffer[8] = is_add ? pAction->data0: 0;
            }
            else
            {
                if (u2_type == SYS_AD_UNION_G_2)
                {
                    return CTC_E_PARAM_CONFLICT;
                }
                SetDsUserId(V, u1_g1_metadataTypeExt_f, ds_userid, is_add? 1: 0);
                SetDsUserId(V, u1_g1_metadataType_f, ds_userid, is_add? CTC_METADATA_TYPE_METADATA: 0);
                SetDsUserId(V, u1_g1_metadata_f, ds_userid, is_add? pAction->data0: 0);
                SetDsUserId(V, u1Type_f, ds_userid, 0);
                SYS_SET_UNION_TYPE(u1_type, SYS_AD_UNION_G_1, DsUserId, 1, ds_userid, is_add);
            }
            break;
        case CTC_SCL_FIELD_ACTION_TYPE_XDATA:
        {
            uint8  loop = 0;
            uint32 chunk_bmp = 0;
            uint32 xdata_value[3]={0};
            ctc_xdata_t xdata;
            ctc_xdata_field_t fields[9];
            ctc_xdata_field_t* p_field = NULL;

            sal_memset(&xdata, 0, sizeof(ctc_xdata_t));
            sal_memset(fields, 0, sizeof(fields));
            
            CTC_ERROR_RETURN(DRV_FROM_AT(lchip)? CTC_E_NONE: CTC_E_NOT_SUPPORT);
           
            
            /*2. get prof*/
            if(is_add)
            {
                CTC_PTR_VALID_CHECK(pAction->ext_data);
                sal_memcpy(&xdata, pAction->ext_data, sizeof(ctc_xdata_t));
                sal_memcpy(fields, xdata.fields, xdata.num * sizeof(ctc_xdata_field_t));
                xdata.fields = fields;
                if(xdata.type != CTC_XDATA_PROF_TYPE_DSSCL)
                {
                    CTC_ERROR_RETURN(CTC_E_INVALID_PARAM);
                }
            }
            else
            {
                xdata.fields = fields;
                xdata.prof_id = GetDsUserId(V, xAdIndex_f, ds_userid);
                xdata.type = CTC_XDATA_PROF_TYPE_DSSCL;
                if(!GetDsUserId(V, xAdEn_f, ds_userid))
                {
                    return CTC_E_NONE;
                }
            }
   
            CTC_ERROR_RETURN(MCHIP_XDATA(lchip)->prof_get_info(lchip, &xdata, is_add));
            GetDsUserId(A, xAdData_f, ds_userid, xdata_value);
            xdata_value[1] = xdata_value[1] & 0x7FFFFFFF;
            
            /*3. build xAdData*/
            for(loop = 0; loop<xdata.num; loop++)
            {
                p_field = xdata.fields+loop;
                if(CTC_FLAG_ISSET(p_field->flag, CTC_XDATA_FIELD_FLAG_UDF))
                {
                    continue;
                }
                CTC_MAX_VALUE_CHECK(p_field->data, (1<<p_field->width)-1);
                _sys_usw_scl_offset_map_chunk(p_field, pe->direction, &chunk_bmp);
                SYS_USW_SET_XDATA(p_field->width, p_field->offset, p_field->data, xdata_value);
            }

            if(CTC_FLAG_ISSET(chunk_bmp, SYS_SCL_XDATA_IGS_CHUNK1_NIBBLE3_0)&&(xdata_value[1] > 0x7FFFFFFF))
            {
                CTC_ERROR_RETURN(CTC_E_INVALID_PARAM);
            }

            SetDsUserId(A, xAdData_f, ds_userid, xdata_value);
            SetDsUserId(V, xAdIndex_f, ds_userid, is_add ? xdata.prof_id : 0);
            SetDsUserId(V, xAdEn_f, ds_userid, is_add ? 1 : 0);
            
            if(CTC_FLAG_ISSET(chunk_bmp, SYS_SCL_XDATA_IGS_CHUNK1_NIBBLE3_0))
            {
                SetDsUserId(V, u1_g1_metadataType_f, ds_userid, 0);
                SetDsUserId(V, u1_g1_metadataTypeExt_f, ds_userid, 0);
                SetDsUserId(V, u1Type_f, ds_userid, 0);
                SYS_SET_UNION_TYPE(u1_type, SYS_AD_UNION_G_1, DsUserId, 1, ds_userid, is_add);
                
            }
            
            if(CTC_FLAG_ISSET(chunk_bmp, SYS_SCL_XDATA_IGS_CHUNK2_BYTE0) || CTC_FLAG_ISSET(chunk_bmp, SYS_SCL_XDATA_IGS_CHUNK2_BYTE1))
            {
                SYS_CHECK_UNION_BITMAP(u2_type, SYS_AD_UNION_G_2);
                SetDsUserId(V, u2_g2_xAdDataValid_f, ds_userid, is_add? 1: 0);
                SetDsUserId(V, u2Type_f, ds_userid, 1);
                SYS_SET_UNION_TYPE(u2_type, SYS_AD_UNION_G_2, DsUserId, 2, ds_userid, is_add);
            }
            if(CTC_FLAG_ISSET(chunk_bmp, SYS_SCL_XDATA_IGS_CHUNK3_WORD0))
            {
                SYS_CHECK_UNION_BITMAP(u3_type, SYS_AD_UNION_G_1);
                SetDsUserId(V, xAdDataValid_f, ds_userid, is_add? 1: 0);
                SetDsUserId(V, u3Type_f, ds_userid, 0);
                SYS_SET_UNION_TYPE(u3_type, SYS_AD_UNION_G_1, DsUserId, 3, ds_userid, is_add);
            }
            break;
        }
        case CTC_SCL_FIELD_ACTION_TYPE_FORCE_BRIDGE:
            if (SYS_SCL_CHK_UNION(u3_type, SYS_AD_UNION_G_2) && SYS_SCL_CHK_UNION(u1_type, SYS_AD_UNION_G_1))
            {
                SYS_SCL_DBG_OUT(CTC_DEBUG_LEVEL_ERROR, "  Both u3 and u1 are used! Line: %u \n", __LINE__);
                return CTC_E_PARAM_CONFLICT;
            }
            field_buffer[5] = is_add? 1: 0;
            break;
        case CTC_SCL_FIELD_ACTION_TYPE_FORCE_LEARNING:
            if (SYS_SCL_CHK_UNION(u3_type, SYS_AD_UNION_G_2) && SYS_SCL_CHK_UNION(u1_type, SYS_AD_UNION_G_1))
            {
                SYS_SCL_DBG_OUT(CTC_DEBUG_LEVEL_ERROR, "  Both u3 and u1 are used! Line: %u \n", __LINE__);
                return CTC_E_PARAM_CONFLICT;
            }
            field_buffer[6] = is_add? 1: 0;
            break;
        case CTC_SCL_FIELD_ACTION_TYPE_FORCE_ROUTE:
            if (SYS_SCL_CHK_UNION(u3_type, SYS_AD_UNION_G_2) && SYS_SCL_CHK_UNION(u1_type, SYS_AD_UNION_G_1))
            {
                SYS_SCL_DBG_OUT(CTC_DEBUG_LEVEL_ERROR, "  Both u3 and u1 are used! Line: %u \n", __LINE__);
                return CTC_E_PARAM_CONFLICT;
            }
            field_buffer[7] = is_add? 1: 0;
            break;
        case CTC_SCL_FIELD_ACTION_TYPE_DENY_LEARNING:
            SetDsUserId(V, denyLearning_f, ds_userid, is_add? 1: 0);
            break;
        case CTC_SCL_FIELD_ACTION_TYPE_DENY_ROUTE:
            SetDsUserId(V, denyRoute_f, ds_userid, is_add? 1: 0);
            break;
        case CTC_SCL_FIELD_ACTION_TYPE_LB_HASH_SELECT_ID:
			temp_ds = SYS_SCL_TEMP_USERID(ds_userid, SYS_SCL_USERID_BMP_FLOW);
            if (GetTempDsFlow(V, flexOpValid_f, temp_ds))
            {
                CTC_ERROR_RETURN(CTC_E_PARAM_CONFLICT);
            }
            if (is_add)
            {
                temp_data = pAction->data0;
                CTC_MAX_VALUE_CHECK(temp_data, 0x7);
                CTC_MIN_VALUE_CHECK(temp_data, 0x1);
            }
            temp_ds = SYS_SCL_TEMP_USERID(ds_userid, SYS_SCL_USERID_BMP_FLOW);
            SetTempDsFlow(V, hashBulkBitmapProfile_f, temp_ds, temp_data);
            break;
        case CTC_SCL_FIELD_ACTION_TYPE_FORCE_DECAP: /*********************************new feature not done*/
            temp_ds = SYS_SCL_TEMP_USERID(ds_userid, SYS_SCL_USERID_BMP_FLOW);
            if (GetTempDsFlow(V, forceSecondParser_f, temp_ds) || GetTempDsFlow(V, flexOpValid_f, temp_ds))
            {
                CTC_ERROR_RETURN(CTC_E_PARAM_CONFLICT);
            }
            if (is_add)
            {
                p_decap = (ctc_scl_force_decap_t*) (pAction->ext_data);
                CTC_PTR_VALID_CHECK(pAction->ext_data);
                CTC_MAX_VALUE_CHECK(p_decap->offset_base_type, CTC_SCL_OFFSET_BASE_TYPE_MAX - 1);
                CTC_MAX_VALUE_CHECK(p_decap->payload_type, 7);
                CTC_MAX_VALUE_CHECK(p_decap->ext_offset, 0x3F);
            }
            SetTempDsFlow(V, innerPacketLookup_f, temp_ds, is_add? p_decap->force_decap_en: 0);
            SetTempDsFlow(V, payloadOffsetStartPoint_f, temp_ds, is_add? p_decap->offset_base_type + 1: 0);
            SetTempDsFlow(V, payloadOffset_f, temp_ds, is_add? p_decap->ext_offset: 0);
            SetTempDsFlow(V, packetType_f, temp_ds, is_add? p_decap->payload_type: 0);
            SetTempDsFlow(V, ttlUpdate_f, temp_ds, is_add? (p_decap->use_outer_ttl? 0: 1): 0);
            /* force decap do not need macth packet outer router mac or enable force route */
            SetTempDsFlow(V, isTunnel_f, temp_ds, is_add? 1: 0);
            break;
        case CTC_SCL_FIELD_ACTION_TYPE_SNOOPING_PARSER: /*********************************new feature not done*/
            temp_ds = SYS_SCL_TEMP_USERID(ds_userid, SYS_SCL_USERID_BMP_FLOW);
            if (GetTempDsFlow(V, isTunnel_f, temp_ds) || GetTempDsFlow(V, flexOpValid_f, temp_ds))
            {
                CTC_ERROR_RETURN(CTC_E_PARAM_CONFLICT);
            }
            p_snooping_parser = (ctc_scl_snooping_parser_t*) (pAction->ext_data);
            if (is_add)
            {
                CTC_PTR_VALID_CHECK(pAction->ext_data);
                CTC_MAX_VALUE_CHECK(p_snooping_parser->start_offset_type, CTC_SCL_OFFSET_BASE_TYPE_MAX - 1);
                CTC_MAX_VALUE_CHECK(p_snooping_parser->payload_type, 7);
            }
            SetTempDsFlow(V, forceSecondParser_f, temp_ds, is_add? (p_snooping_parser->enable? 1: 0): 0);
            SetTempDsFlow(V, innerPacketLookup_f, temp_ds, 0);
            SetTempDsFlow(V, payloadOffsetStartPoint_f, temp_ds, is_add? (p_snooping_parser->start_offset_type + 1): 0);
            SetTempDsFlow(V, payloadOffset_f, temp_ds, is_add? p_snooping_parser->ext_offset: 0);
            SetTempDsFlow(V, packetType_f, temp_ds, is_add? p_snooping_parser->payload_type: 0);
            SetTempDsFlow(V, forceUseInnerDoHash_f, temp_ds, is_add? (p_snooping_parser->use_inner_hash_en? 1: 0): 0);
            /* snooping parser do not need macth packet outer router mac or enable force route */
            SetTempDsFlow(V, isTunnel_f, temp_ds, 0);
            break;
        case CTC_SCL_FIELD_ACTION_TYPE_IGMP_SNOOP_EN:
            SetDsUserId(V, u1_g1_igmpSnoopEn_f, ds_userid, is_add && pAction->data0? 1: 0);
            SetDsUserId(V, u1_g1_igmpSnoopEnValid_f, ds_userid, is_add? 1: 0);
            SYS_SET_UNION_TYPE(u1_type, SYS_AD_UNION_G_1, DsUserId, 1, ds_userid, is_add);
            break;
        /*for pon*/
        case SYS_SCL_FIELD_ACTION_TYPE_PON_SERVICE:
            CTC_MAX_VALUE_CHECK(pAction->data0, 1);
            temp_ds = SYS_SCL_TEMP_USERID(ds_userid, SYS_SCL_USERID_BMP_LOGIC_PORT);
            SetTempDsLogicPort(V, ponRuleType_f, temp_ds, pAction->data0);
            break;
        case SYS_SCL_FIELD_ACTION_TYPE_DOT1AE_SCID:
            SYS_TMM_SCL_UPDATE_DSFWD();
            SYS_CHECK_UNION_BITMAP(fwd_u_type, SYS_AD_UNION_G_2);
            temp_ds = SYS_SCL_TEMP_USERID(ds_userid, SYS_SCL_USERID_BMP_FWD);
            if (GetTempDsFwdInfo(V, u_g2_ecmpGroupId_f, temp_ds) && !GetTempDsFwdInfo(V, u_g2_advMacsecEnable_f, temp_ds))
            {
                CTC_ERROR_RETURN(CTC_E_PARAM_CONFLICT);
            }
            SetTempDsFwdInfo(V, u_g2_advMacsecEnable_f, temp_ds, is_add? 1: 0);
            if (pAction->ext_data)
            {
                SetTempDsFwdInfo(V, u_g2_ecmpGroupId_f, temp_ds, is_add? ((pAction->data1<<8) | pAction->data0): 0);
            }
            else
            {
                SetTempDsFwdInfo(V, u_g2_ecmpGroupId_f, temp_ds, is_add? pAction->data0: 0);
            }
            SYS_SET_UNION_TYPE(fwd_u_type, SYS_AD_UNION_G_2, TempDsFwdInfo, , temp_ds, is_add);
            SetTempDsFwdInfo(V, uType_f, temp_ds, fwd_u_type == SYS_AD_UNION_G_NA? 0: 1);
            break;

        case CTC_SCL_FIELD_ACTION_TYPE_FLEX_EDIT:
        {
            ctc_scl_flex_edit_t* flex_edit = (ctc_scl_flex_edit_t*)pAction->ext_data;
            temp_ds = SYS_SCL_TEMP_USERID(ds_userid, SYS_SCL_USERID_BMP_FLOW);
            if (GetTempDsFlow(V, forceSecondParser_f, temp_ds) || GetTempDsFlow(V, isTunnel_f, temp_ds)
                || CTC_BMP_ISSET(pe->action_bmp, CTC_SCL_FIELD_ACTION_TYPE_LB_HASH_SELECT_ID) || 
                   CTC_BMP_ISSET(pe->action_bmp, CTC_SCL_FIELD_ACTION_TYPE_L3IF_PROPERTY) ||
                   CTC_BMP_ISSET(pe->action_bmp, SYS_SCL_FIELD_ACTION_TYPE_SRV6))
            {
                CTC_ERROR_RETURN(CTC_E_PARAM_CONFLICT);
            }
            if (is_add)
            {
                CTC_MAX_VALUE_CHECK(flex_edit->start_offset_type, CTC_SCL_OFFSET_BASE_TYPE_MAX-1);
                if ((0 != flex_edit->start_offset % 2) || (0 !=  flex_edit->len % 2))
                {
                    return CTC_E_INVALID_PARAM;
                }
            }
            SetTempDsFlow(V, flexOpValid_f, temp_ds, is_add? 1 : 0);
            SetTempDsFlow(V, hashBulkBitmapProfile_f, temp_ds, is_add? (flex_edit->start_offset_type + 1): 0);

            /* Config flexOpStart */
            SetTempDsFlow(V, startOffsetUdfSel_f, temp_ds, is_add? ((flex_edit->start_offset >> 6)& 0x3) : 0);
            SetTempDsFlow(V, routerMacProfileId_f, temp_ds, is_add? (flex_edit->start_offset & 0x3f) : 0);

            /* Config flexOpOffset */
            SetTempDsFlow(V, payloadOffsetUdfSel_f, temp_ds, is_add? ((flex_edit->len >> 6)& 0x3) : 0);
            SetTempDsFlow(V, payloadOffset_f, temp_ds, is_add? (flex_edit->len & 0x3f) : 0);
            break;
        }

        case SYS_SCL_FIELD_ACTION_TYPE_SRV6:
        {
            #define SYS_ETH_HEADER_CHECK_OFFSET 2    /*gAluNxtHdr_2_value_f for ETH*/
            #define SYS_SRH_CHECK_DIS 7              /* Disable check SRH */
            sys_scl_srv6_t* srv6 = (sys_scl_srv6_t*)pAction->ext_data;
            if (CTC_BMP_ISSET(pe->action_bmp, CTC_SCL_FIELD_ACTION_TYPE_L3IF_PROPERTY) || CTC_BMP_ISSET(pe->action_bmp, CTC_SCL_FIELD_ACTION_TYPE_FLEX_EDIT))
            {
                return CTC_E_PARAM_CONFLICT;
            }
            if (srv6->fid)
            {
                temp_ds = SYS_SCL_TEMP_USERID(ds_userid, SYS_SCL_USERID_BMP_LOGIC_PORT);
                SetTempDsLogicPort(V, vsiIdOrUserVlanPtr_f, temp_ds, is_add? srv6->fid : 0);
                SetTempDsLogicPort(V, vsiIdValid_f, temp_ds, is_add? 1 : 0);
            }
            temp_ds = SYS_SCL_TEMP_USERID(ds_userid, SYS_SCL_USERID_BMP_FLOW);
            SetTempDsFlow(V, ttlCheckEn_f, temp_ds, srv6->ttl_chk);
            SetTempDsFlow(V, packetType_f, temp_ds, srv6->pkt_type);
            SetTempDsFlow(V, payloadOffsetStartPoint_f, temp_ds, srv6->strip_type);
            SetTempDsFlow(V, forceSecondParser_f, temp_ds, srv6->second_parser);
            SetTempDsFlow(V, innerPacketLookup_f, temp_ds, srv6->inner_lookup);
            if (DRV_FROM_AT(lchip))
            {
                SYS_CHECK_UNION_BITMAP(u2_type, SYS_AD_UNION_G_3);
                SetTempDsFlow(V, flexOpValid_f, temp_ds, 1);
                if (srv6->is_usid)   /* uSID */
                {
                    SetTempDsFlow(V, hashBulkBitmapProfile_f, temp_ds, (0 << 2) | 2);                /* flexOpStartPoint(Layer3) | flexOpStartIsVariable(disable) */
                    SetTempDsFlow(V, routerMacProfileId_f, temp_ds, (srv6->user_def_offset & 0x3F)); /* flexOpStart */

                    SetDsUserId(V, u2_g3_sr6_nxtSidType_f, ds_userid, 2);                            /* uSID */
                    SetDsUserId(V, u2_g3_sr6_flexEditType_f, ds_userid, 1);                          /* uSID */

                    SetDsUserId(V, u2_g3_sr6_aluFlag_f, ds_userid, 1);
                    SetDsUserId(V, u2_g3_sr6_aluNxtHdr0_f, ds_userid, 0);
                    SetDsUserId(V, u2_g3_sr6_aluNxtHdr1_f, ds_userid, 0);
                    SetDsUserId(V, u2_g3_sr6_srhSlCheckEn_f, ds_userid, 0);
                    SetDsUserId(V, u2_g3_sr6_srhCheckEn_f, ds_userid, 1);

                    SYS_CHECK_UNION_BITMAP(u3_type, SYS_AD_UNION_G_2);
                    SetDsUserId(V, u3_g2_efdAction_f, ds_userid, 1);                                 /* srhPopCheckEn | srhPopCheckId */
                    SYS_SET_UNION_TYPE(u3_type, SYS_AD_UNION_G_2, DsUserId, 3, ds_userid, is_add);
                    SetDsUserId(V, u3Type_f, ds_userid, (u3_type == SYS_AD_UNION_G_NA)? 0 : 1);
                }
                else if (srv6->is_gsid && srv6->coc_flavor)   /* gSID */
                {
                    SetTempDsFlow(V, hashBulkBitmapProfile_f, temp_ds, (1 << 2) | 2);   /* flexOpStartPoint(Layer3) | flexOpStartIsVariable(enable) */
                    SetTempDsFlow(V, startOffsetUdfSel_f, temp_ds, 0);                  /* choose SL */
                    SetTempDsFlow(V, startOffsetShift_f, temp_ds, (0 << 3) | 4);        /* SL multiply 16 */
                    SetTempDsFlow(V, routerMacProfileId_f, temp_ds, (48 - 4));          /* flexOpStart */

                    SetDsUserId(V, u2_g3_sr6_aluNxtHdr0_f, ds_userid, 0);
                    SetDsUserId(V, u2_g3_sr6_aluNxtHdr1_f, ds_userid, 0);
                    SetDsUserId(V, u2_g3_sr6_nxhHdrMode_f, ds_userid, 0);
                    SetDsUserId(V, u2_g3_sr6_aluFlag_f, ds_userid, 1);

                    SetTempDsFlow(V, payloadOffsetUdfSel_f, temp_ds, 2);
                    SetTempDsFlow(V, payloadOffsetIsVariable_f, temp_ds, 1);
                    SetTempDsFlow(V, payloadOffsetShift_f, temp_ds, (0 << 3) | 3);
                    SetTempDsFlow(V, payloadOffset_f, temp_ds, 8);

                    SetDsUserId(V, u2_g3_sr6_srhSlCheckEn_f, ds_userid, 0);
                    SetDsUserId(V, u2_g3_sr6_srhCheckEn_f, ds_userid, 1);
                    SetDsUserId(V, u2_g3_sr6_flexEditType_f, ds_userid, 2);             /* gSID */
                    SetDsUserId(V, u2_g3_sr6_nxtSidType_f, ds_userid, 3);               /* gSID */
                    SetDsUserId(V, u2_g3_sr6_pspEn_f, ds_userid, srv6->psp_en ? 1 : 0);

                    SYS_CHECK_UNION_BITMAP(u3_type, SYS_AD_UNION_G_2);
                    SetDsUserId(V, u3_g2_efdAction_f, ds_userid, 3);                    /* srhPopCheckEn | srhPopCheckId */
                    SetDsUserId(V, u3_g2_ptpIndex_f, ds_userid, srv6->psp_en ? 3 : 0);    /* do psp */
                    SYS_SET_UNION_TYPE(u3_type, SYS_AD_UNION_G_2, DsUserId, 3, ds_userid, is_add);
                    SetDsUserId(V, u3Type_f, ds_userid, (u3_type == SYS_AD_UNION_G_NA)? 0 : 1);

                }
                else   /* Normal sid */
                {
                    SetDsUserId(V, u2_g3_sr6_aluFlag_f, ds_userid, 1);
                    SetDsUserId(V, u2_g3_sr6_pspEn_f, ds_userid, srv6->psp_en ? 1 : 0);
                    SetDsUserId(V, u2_g3_sr6_uspEn_f, ds_userid, srv6->usp_en ? 1 : 0);
                    SetDsUserId(V, u2_g3_sr6_usdEn_f, ds_userid, (srv6->usd_en || srv6->is_decap) ? 1 : 0);

                    if (srv6->is_decap || srv6->usd_en)
                    {
                        SetTempDsFlow(V, flexOpValid_f, temp_ds, 0);
                        SetTempDsFlow(V, isTunnel_f, temp_ds, 1);
                        SetTempDsFlow(V, ttlUpdate_f, temp_ds, (srv6->use_outer_ttl ? 0 : 1));
                        SetTempDsFlow(V, routerMacProfileId_f, temp_ds, srv6->router_mac_profile);  /* innerRouterMacProfile */
                        SetDsUserId(V, auxData_f, ds_userid, (srv6->router_mac_profile >> 6));
                        SetDsUserId(V, u2_g3_sr6_aluNxtHdr0_f, ds_userid, ((srv6->router_mac_profile) ? 0 : ((srv6->pkt_type == PKT_TYPE_IP) ? PKT_TYPE_IPV4 : ((srv6->pkt_type == PKT_TYPE_ETH) ? (PKT_TYPE_ETH + SYS_ETH_HEADER_CHECK_OFFSET) : srv6->pkt_type)))); /* END.DT using innerRouterMac and do not check nextHeader */
                        SetDsUserId(V, u2_g3_sr6_aluNxtHdr1_f, ds_userid, ((srv6->router_mac_profile) ? 0 : ((srv6->pkt_type == PKT_TYPE_IP) ? PKT_TYPE_IPV6 : ((srv6->pkt_type == PKT_TYPE_ETH) ? (PKT_TYPE_ETH + SYS_ETH_HEADER_CHECK_OFFSET) : srv6->pkt_type)))); /* END.DT using innerRouterMac and do not check nextHeader */
                        SetDsUserId(V, u2_g3_sr6_nxhHdrMode_f, ds_userid, (srv6->pkt_type == PKT_TYPE_IP) ? 1 : 0);
                        SetDsUserId(V, u2_g3_sr6_srhSlCheckEn_f, ds_userid, srv6->usd_en ? 0 : 1);
                        SetDsUserId(V, u2_g3_sr6_srhCheckEn_f, ds_userid, 0);
                        SetDsUserId(V, u2_g3_sr6_flexEditType_f, ds_userid, 3);                     /* disable */
                    }
                    else
                    {
                        SetDsUserId(V, u2_g3_sr6_aluNxtHdr0_f, ds_userid, 0);
                        SetDsUserId(V, u2_g3_sr6_aluNxtHdr1_f, ds_userid, 0);
                        SetDsUserId(V, u2_g3_sr6_nxhHdrMode_f, ds_userid, 0);
                        SetDsUserId(V, u2_g3_sr6_flexEditType_f, ds_userid, 0);                     /* normal SID */
                        SetDsUserId(V, u2_g3_sr6_nxtSidType_f, ds_userid, 1);                       /* normal SID */
                        SetDsUserId(V, u2_g3_sr6_srhSlCheckEn_f, ds_userid, srv6->usp_en ? 0 : 2);
                        SetDsUserId(V, u2_g3_sr6_srhCheckEn_f, ds_userid, 1);

                        SetTempDsFlow(V, hashBulkBitmapProfile_f, temp_ds, (1 << 2) | 2); /* flexOpStartPoint(Layer3) | flexOpStartIsVariable(enable) */
                        SetTempDsFlow(V, startOffsetUdfSel_f, temp_ds, 0);                /* choose SL */
                        SetTempDsFlow(V, startOffsetShift_f, temp_ds, (0 << 3) | 4);      /* SL multiply 16 */
                        SetTempDsFlow(V, routerMacProfileId_f, temp_ds, (48 - 16));       /* flexOpStart */

                        SetTempDsFlow(V, payloadOffsetUdfSel_f, temp_ds, 2);              /* Hdr Ext Len */
                        SetTempDsFlow(V, payloadOffsetIsVariable_f, temp_ds, 1);
                        SetTempDsFlow(V, payloadOffsetShift_f, temp_ds, (0 << 3) | 3);    /* Hdr Ext Len multiply 8 */
                        SetTempDsFlow(V, payloadOffset_f, temp_ds, 8);                    /* SRH Len 8 */
                    }
                }

                if (srv6->is_user_def)
                {
                    SetTempDsFlow(V, hashBulkBitmapProfile_f, temp_ds, (srv6->edit_offset_cal << 2) | 2);  /* flexOpStartPoint(Layer3) | flexOpStartIsVariable(enable/disable)*/
                    SetTempDsFlow(V, startOffsetUdfSel_f, temp_ds, (srv6->user_def_offset >> 6));     /* choose SL */
                    SetTempDsFlow(V, routerMacProfileId_f, temp_ds, (srv6->user_def_offset & 0x3F));  /* flexOpStart */
                    SetDsUserId(V, u2_g3_sr6_flexEditType_f, ds_userid, srv6->edit_type);
                }

                if (SYS_SRH_CHECK_DIS == srv6->op_type)  /* Disable check SRH */
                {
                    SetDsUserId(V, u2_g3_sr6_aluNxtHdr0_f, ds_userid, 0);                       /* Disable check Next Header */
                    SetDsUserId(V, u2_g3_sr6_aluNxtHdr1_f, ds_userid, 0);                       /* Disable check Next Header */
                    SetDsUserId(V, u2_g3_sr6_srhSlCheckEn_f, ds_userid, 0);                     /* Disable check SL */
                    SetDsUserId(V, u2_g3_sr6_aluFlag_f, ds_userid, 0);                          /* Disable check FLAG */
                    SetDsUserId(V, u2_g3_sr6_srhCheckEn_f, ds_userid, 0);                       /* Disable check SRH valid */
                }

                SYS_SET_UNION_TYPE(u2_type, SYS_AD_UNION_G_3, DsUserId, 2, ds_userid, is_add);
                SetDsUserId(V, u2Type_f, ds_userid, (u2_type == SYS_AD_UNION_G_NA)? 0 : 2);
            }
            else
            {
                /* this logic used for normal sid/usid/gsid reserved tcam and gsid */
                if (srv6->is_usid)/* usid */
                {
                    SetDsUserId(V, isLeaf_f, ds_userid, 1);
                }
                if (srv6->is_gsid_rsv) /* only for gsid reserved tcam */
                {
                    SYS_CHECK_UNION_BITMAP(u1_type, SYS_AD_UNION_G_1);
                    SetDsUserId(V, u1_g1_metadataTypeExt_f, ds_userid, is_add ? 1 : 0);
                    SetDsUserId(V, u1_g1_metadataType_f, ds_userid, 0);
                    SetDsUserId(V, u1_g1_metadata_f, ds_userid, is_add ? srv6->edit_ptr : 0);
                    SYS_SET_UNION_TYPE(u1_type, SYS_AD_UNION_G_1, DsUserId, 1, ds_userid, is_add);
                    SetDsUserId(V, u1Type_f, ds_userid, 0);

                    SYS_CHECK_UNION_BITMAP(u2_type, SYS_AD_UNION_G_1);
                    SetDsUserId(V, u2_g1_udfHitIndex_f, ds_userid, is_add ? srv6->udf_idx : 0);
                    SYS_SET_UNION_TYPE(u2_type, SYS_AD_UNION_G_1, DsUserId, 2, ds_userid, is_add);
                    SetDsUserId(V, u2Type_f, ds_userid, 0);

                    SetTempDsFlow(V, payloadOffset_f, temp_ds, srv6->psp_en ? srv6->hdr_len : 0);
                }
                else if (!srv6->is_gsid || !srv6->coc_flavor) /* only for normal sid and usid */
                {
                    SYS_CHECK_UNION_BITMAP(u2_type, SYS_AD_UNION_G_3);
                    SetDsUserId(V, u2_g3_srEditPtr_f, ds_userid, is_add? srv6->edit_ptr : 0);
                    SetDsUserId(V, u2_g3_srLookupEn_f, ds_userid, is_add? srv6->lookup_en  : 0);
                    SetDsUserId(V, u2_g3_srOpType_f, ds_userid, is_add? srv6->op_type  : 0);
                    SetDsUserId(V, u2_g3_srPspEn_f, ds_userid, is_add? srv6->psp_en  : 0);
                    SYS_SET_UNION_TYPE(u2_type, SYS_AD_UNION_G_3, DsUserId, 2, ds_userid, is_add);
                    SetDsUserId(V, u2Type_f, ds_userid, (u2_type == SYS_AD_UNION_G_NA)? 0 : 2);
                }
                if(srv6->is_user_def) /* used for gsid reserved tcam and usid */
                {
                    SetTempDsFlow(V, flexOpValid_f, temp_ds, 1);
                	SetTempDsFlow(V, hashBulkBitmapProfile_f, temp_ds, (srv6->edit_offset_cal << 2) | 2); /*flexOpStartIsVariable(0,0), flexOpStartPoint(1,0)*/
                    SetTempDsFlow(V, routerMacProfileId_f, temp_ds, (srv6->user_def_offset & 0x3F));
                    SetTempDsFlow(V, startOffsetUdfSel_f, temp_ds, (srv6->user_def_offset >> 6));
                	SetTempDsFlow(V, startOffsetShift_f, temp_ds, 4);                 /* sizeof SID, means 16bytes*/
                }
            	else if ((srv6->sid_swap && !srv6->is_gsid) || (!srv6->coc_flavor && srv6->is_gsid)) /* for normal sid or coc flavor of gsid*/
                {
                    SetTempDsFlow(V, flexOpValid_f, temp_ds, 1);
                    SetTempDsFlow(V, hashBulkBitmapProfile_f, temp_ds, (1 << 2) | 2); /* flexOpStartIsVariable(0,0), flexOpStartPoint(1,0) */

                	/* Config flexOpStart */
                    SetTempDsFlow(V, startOffsetUdfSel_f, temp_ds, 0);                /* select SL from udf*/
                    SetTempDsFlow(V, startOffsetShift_f, temp_ds, 4);                 /* sizeof SID, means 16bytes*/
                    SetTempDsFlow(V, routerMacProfileId_f, temp_ds, (48 - 16));

                	/* Config flexOpOffset */
                	SetTempDsFlow(V, payloadOffsetUdfSel_f, temp_ds, 2);              /* Select Header Ext Length from udf */
                	SetTempDsFlow(V, payloadOffsetIsVariable_f, temp_ds, 1);          /* Enable calculate flexOpOffset */
                	SetTempDsFlow(V, payloadOffset_f, temp_ds, 8);                    /* The length of SRH (8Byte) */
                	SetTempDsFlow(V, payloadOffsetShift_f, temp_ds, 3);               /* (Header Ext Length) << 3 */
                }
                else if ((!srv6->sid_swap && srv6->is_gsid) || !srv6->is_gsid)        /* used for gSID decap or uSID and Normal SID decap */
                {
                    SetTempDsFlow(V, isTunnel_f, temp_ds, 1);
                    SetTempDsFlow(V, ttlUpdate_f, temp_ds, (srv6->use_outer_ttl?0:1));
                	SetTempDsFlow(V, routerMacProfileId_f, temp_ds, srv6->router_mac_profile); /* END.DT using innerRouterMac and do not check nextHeader */
            	}
		    }
        }
            break;
        case CTC_SCL_FIELD_ACTION_TYPE_CANCEL_LKUP_BMP:
        {
            uint8 scl_id = (pe->is_default) ?  pAction->data1 : pe->group_priority;
            uint8 hi_bits = 0;
            uint8 lo_bits = 0;
            uint8 clear_bmp = 0;
            uint8 mask_array[4] = {0,0x01,0x03,0x07};

            CTC_MAX_VALUE_CHECK(pAction->data0, 0xf);
            CTC_MAX_VALUE_CHECK(pAction->data1, 3);
            hi_bits = pAction->data0 >> (scl_id + 1);
            lo_bits = pAction->data0 & mask_array[scl_id];
            clear_bmp = (hi_bits << scl_id) | lo_bits;
            SetDsUserId(V, clearSclRsltBmp_f, ds_userid, is_add ? clear_bmp : 0);
        }
            break;
        case CTC_SCL_FIELD_ACTION_TYPE_CHANGE_LKUP_PRI:
        {
            CTC_MAX_VALUE_CHECK(pAction->data0, 7);
            SetDsUserId(V, clearSclRsltBmp_f, ds_userid, is_add ? pAction->data0 : 0);
            break;
        }
        case CTC_SCL_FIELD_ACTION_TYPE_ARP_ACTION:
        {
            if (is_add)
            {
                CTC_MAX_VALUE_CHECK(pAction->data0, MAX_CTC_EXCP_TYPE - 1);
                SetDsUserId(V, u1_g1_arpCtlEn_f, ds_userid, 1);
                SetDsUserId(V, u1_g1_arpExceptionType_f, ds_userid, pAction->data0);
            }
            else
            {
                SetDsUserId(V, u1_g1_arpCtlEn_f, ds_userid, 0);
                SetDsUserId(V, u1_g1_arpExceptionType_f, ds_userid, 0);
            }
            SYS_SET_UNION_TYPE(u1_type, SYS_AD_UNION_G_1, DsUserId, 1, ds_userid, is_add);
            break;
        }

        case CTC_SCL_FIELD_ACTION_TYPE_IPV4_BASED_L2MC :
            SetDsUserId(V, u1_g1_forceIpv4Lookup_f, ds_userid, (is_add? pAction->data0& 1: 0));
            SetDsUserId(V, u1_g1_forceIpv4LookupEn_f, ds_userid, (is_add? 1: 0));
            SYS_SET_UNION_TYPE(u1_type, SYS_AD_UNION_G_1, DsUserId, 1, ds_userid, is_add);
            break;
        case CTC_SCL_FIELD_ACTION_TYPE_IPV6_BASED_L2MC :
            SetDsUserId(V, u1_g1_forceIpv6Lookup_f, ds_userid, (is_add? pAction->data0 & 1: 0));
            SetDsUserId(V, u1_g1_forceIpv6LookupEn_f, ds_userid, (is_add? 1: 0));
            SYS_SET_UNION_TYPE(u1_type, SYS_AD_UNION_G_1, DsUserId, 1, ds_userid, is_add);
            break;

        case CTC_SCL_FIELD_ACTION_TYPE_IPFIX_LKUP_BY_OUTER_HEAD:
            CTC_MAX_VALUE_CHECK(pAction->data0, 1);
            field_buffer[3] = is_add? pAction->data0: 0;
            break;

        case CTC_SCL_FIELD_ACTION_TYPE_RANDOM_LOG:
        {
            uint8 log_id = 0;
            uint8 session_id = 0;
            uint8 percent = 0;
            ctc_acl_log_t *p_log = NULL;

            if (is_add)
            {
                CTC_PTR_VALID_CHECK(pAction->ext_data);
                p_log = (ctc_acl_log_t*)(pAction->ext_data);
                if (CTC_BMP_ISSET(pe->action_bmp, CTC_SCL_FIELD_ACTION_TYPE_ISOLATION_ID))
                {
                    return CTC_E_PARAM_CONFLICT;
                }
                log_id = p_log->log_id;
                session_id = p_log->session_id;
                percent = p_log->percent;

                CTC_MAX_VALUE_CHECK(log_id, 1);
                CTC_MAX_VALUE_CHECK(session_id, MCHIP_CAP(SYS_CAP_ACL_MAX_SESSION) - 1);
                CTC_VALUE_RANGE_CHECK(percent, CTC_LOG_PERCENT_POWER_NEGATIVE_14, CTC_LOG_PERCENT_POWER_NEGATIVE_0);
            }
            else
            {
                log_id = field_buffer[4] >> 24;
            }
            field_buffer[4] = is_add? (log_id<<24)|(session_id<<16)|(percent): 0;
        }
        break;

        case CTC_SCL_FIELD_ACTION_TYPE_COS_HBWP_POLICER:
            if (is_add)
            {
                CTC_MAX_VALUE_CHECK(pAction->data1, MCHIP_CAP(SYS_CAP_QOS_POLICER_MAX_COS_LEVEL) -1);
                CTC_NOT_ZERO_CHECK(pAction->data0);

                policer_param.policer_id = pAction->data0;
                policer_param.sys_policer_type = SYS_QOS_POLICER_TYPE_FLOW;
                policer_param.glb_policer = !MCHIP_FEATURE_PP_EN(lchip,CTC_FEATURE_SCL);
                CTC_ERROR_RETURN(sys_usw_qos_policer_index_get(lchip, &policer_param));
                if(!policer_param.is_bwp)
                {
                    return CTC_E_INVALID_PARAM;
                }

                SetDsUserId(V, policerPhbEn_f, ds_userid, 0);
                SetDsUserId(V, policerLvlSel_f, ds_userid, policer_param.level);
                SetDsUserId(V, policerPtr_f, ds_userid, policer_param.policer_ptr+pAction->data1);            
            }
            else
            {
                SetDsUserId(V, policerPhbEn_f, ds_userid, 0);
                SetDsUserId(V, policerLvlSel_f, ds_userid, 0);
                SetDsUserId(V, policerPtr_f, ds_userid, 0);           
            }
            break;
        case CTC_SCL_FIELD_ACTION_TYPE_ISOLATION_ID:
            CTC_MAX_VALUE_CHECK(pAction->data0, MCHIP_CAP(SYS_CAP_ISOLATION_ID_MAX));
            SYS_CHECK_UNION_BITMAP(u3_type, SYS_AD_UNION_G_2);
            /* CTC_SCL_FIELD_ACTION_TYPE_RANDOM_LOG */
            if (CTC_BMP_ISSET(pe->action_bmp, CTC_SCL_FIELD_ACTION_TYPE_RANDOM_LOG))
            {
                return CTC_E_PARAM_CONFLICT;
            }

            SetDsUserId(V, u3_g2_aclLogId_f, ds_userid, is_add ? 0x2 : 0);
            SetDsUserId(V, u3_g2_aclLogLevel_f, ds_userid, is_add ? ((pAction->data0>>4) &0x1) : 0);
            SetDsUserId(V, u3_g2_randomThresholdShift_f, ds_userid, is_add ? ((pAction->data0) &0xF) : 0);
            SetDsUserId(V, u3_g2_srcPortIsolateIdValid_f, ds_userid, is_add ? 1 : 0);

            SYS_SET_UNION_TYPE(u3_type,SYS_AD_UNION_G_2,DsUserId,3,ds_userid, is_add);
            SetDsUserId(V, u3Type_f, ds_userid, (u3_type == SYS_AD_UNION_G_NA) ? 0 : 1);
            break;

        case CTC_SCL_FIELD_ACTION_TYPE_L3IF_PROPERTY:
        {
            mac_addr_t zero_mac;
            mac_addr_t* mac;
            uint16 route_mac_index = 0;
            uint8 value = 0;

            temp_ds = SYS_SCL_TEMP_USERID(ds_userid, SYS_SCL_USERID_BMP_FLOW);
            if (GetTempDsFlow(V, flexOpValid_f, temp_ds))/* CTC_SCL_FIELD_ACTION_TYPE_FLEX_EDIT */
            {
                return CTC_E_PARAM_CONFLICT;
            }

            if (is_add)
            {
                switch (pAction->data0)
                {
                    case CTC_L3IF_PROP_ROUTE_MAC_LOW_8BITS:
                        CTC_PTR_VALID_CHECK(pAction->ext_data);
                        mac = (mac_addr_t*)pAction->ext_data;
                        sal_memset(&zero_mac, 0, sizeof(mac_addr_t));
                        if (!sal_memcmp(&zero_mac, mac, sizeof(mac_addr_t)))
                        {
                            return CTC_E_INVALID_PARAM;
                        }
                        if (pe->u.temp_entry->temp_ad.inner_rmac_index)
                        {
                            sys_usw_l3if_unbinding_inner_router_mac(lchip, pe->u.temp_entry->temp_ad.inner_rmac_index);
                        }
                        CTC_ERROR_RETURN(sys_usw_l3if_binding_inner_router_mac(lchip, mac, &route_mac_index));
                        value = (1 << 3 | ((route_mac_index >> 6) & 0x7));
                        SetDsUserId(V, auxData_f, ds_userid, value);
                        SetTempDsFlow(V, flexOpValid_f, temp_ds, 0);
                        SetTempDsFlow(V, routerMacProfileId_f, temp_ds, route_mac_index & 0x3f);
                        pe->u.temp_entry->temp_ad.inner_rmac_index = route_mac_index;
                        break;
                    default:
                        SYS_SCL_DBG_OUT(CTC_DEBUG_LEVEL_ERROR, " API or some feature is not supported \n");
                        return CTC_E_NOT_SUPPORT;
                }
            }
            else if(pe->u.temp_entry->temp_ad.inner_rmac_index)
            {
                CTC_ERROR_RETURN(sys_usw_l3if_unbinding_inner_router_mac(lchip, pe->u.temp_entry->temp_ad.inner_rmac_index));
                SetTempDsFlow(V, routerMacProfileId_f, temp_ds, 0);
                SetDsUserId(V, auxData_f, ds_userid, 0);
                pe->u.temp_entry->temp_ad.inner_rmac_index = 0;
            }
            break;
        }
        default:
            SYS_SCL_DBG_OUT(CTC_DEBUG_LEVEL_ERROR, " API or some feature is not supported \n");
            CTC_ERROR_RETURN(CTC_E_NOT_SUPPORT);
    }
    
    


    if (!is_add &&
        (pAction->type == CTC_SCL_FIELD_ACTION_TYPE_REDIRECT ||
        pAction->type == CTC_SCL_FIELD_ACTION_TYPE_REDIRECT_PORT ||
        pAction->type == CTC_SCL_FIELD_ACTION_TYPE_DISCARD))
    {
        CTC_BIT_UNSET(fwd_bmp, 2);
    }
    else if (!is_add && CTC_SCL_FIELD_ACTION_TYPE_FID == pAction->type)
    {
        CTC_BIT_UNSET(fwd_bmp, 1);
    }
    else if (!is_add && CTC_SCL_FIELD_ACTION_TYPE_VRFID == pAction->type)
    {
        CTC_BIT_UNSET(fwd_bmp, 0);
    }
    
    if ( pe->u.temp_entry->temp_ad.com.u1_type == SYS_AD_UNION_G_1 || u1_type == SYS_AD_UNION_G_1 )   /*sync u1g1, due to no u1g1 ds*/
    {
        GetDsUserId(A, u1_data_f, ds_userid, SYS_SCL_TEMP_USERID(ds_userid, SYS_SCL_USERID_BMP_U1_G1));
    }
    /*set use outer status*/
    if ( CTC_BMP_ISSET(pe->action_bmp, CTC_SCL_FIELD_ACTION_TYPE_FLOW_LKUP_BY_OUTER_HEAD) ||
         CTC_BMP_ISSET(pe->action_bmp, CTC_SCL_FIELD_ACTION_TYPE_VRFID) ||
         CTC_BMP_ISSET(pe->action_bmp, CTC_SCL_FIELD_ACTION_TYPE_IPFIX_LKUP_BY_OUTER_HEAD) ||
         CTC_BMP_ISSET(pe->action_bmp, CTC_SCL_FIELD_ACTION_TYPE_RANDOM_LOG) ||
         CTC_BMP_ISSET(pe->action_bmp, CTC_SCL_FIELD_ACTION_TYPE_FORCE_BRIDGE) ||
         CTC_BMP_ISSET(pe->action_bmp, CTC_SCL_FIELD_ACTION_TYPE_FORCE_LEARNING) ||
         CTC_BMP_ISSET(pe->action_bmp, CTC_SCL_FIELD_ACTION_TYPE_FORCE_ROUTE) ||
         CTC_BMP_ISSET(pe->action_bmp, CTC_SCL_FIELD_ACTION_TYPE_METADATA) ||
         (pAction->type == CTC_SCL_FIELD_ACTION_TYPE_FLOW_LKUP_BY_OUTER_HEAD) ||
         (pAction->type == CTC_SCL_FIELD_ACTION_TYPE_VRFID) ||
         (pAction->type == CTC_SCL_FIELD_ACTION_TYPE_IPFIX_LKUP_BY_OUTER_HEAD) ||
         (pAction->type == CTC_SCL_FIELD_ACTION_TYPE_RANDOM_LOG) ||
         (pAction->type == CTC_SCL_FIELD_ACTION_TYPE_FORCE_BRIDGE) ||
         (pAction->type == CTC_SCL_FIELD_ACTION_TYPE_FORCE_LEARNING) ||
         (pAction->type == CTC_SCL_FIELD_ACTION_TYPE_FORCE_ROUTE)||
         (pAction->type == CTC_SCL_FIELD_ACTION_TYPE_METADATA))
    {
        CTC_ERROR_RETURN(_sys_tmm_scl_set_new_action_field(lchip, is_add, fwd_bmp, &u1_type, &u2_type, &u3_type, &fwd_u_type, &userid_bmp, field_buffer, ds_userid, pe, pAction));
    }

    if (!is_add && no_aset)
    {
        CTC_ERROR_RETURN(_sys_tmm_scl_map_action_field_to_userid_bmp(lchip, pAction, pe, ds_userid, &userid_bmp, FALSE));
    }

    SYS_USW_SCL_SET_BMP(pe->action_bmp, pAction->type, is_add);
    
    if (pAction->type == CTC_SCL_FIELD_ACTION_TYPE_SRC_CID)
    {
        SYS_USW_SCL_SET_BMP(pe->action_bmp, CTC_SCL_FIELD_ACTION_TYPE_DST_CID, 0);
    }
    if (pAction->type == CTC_SCL_FIELD_ACTION_TYPE_DST_CID)
    {
        SYS_USW_SCL_SET_BMP(pe->action_bmp, CTC_SCL_FIELD_ACTION_TYPE_SRC_CID, 0);
    }

    _sys_tmm_scl_move_temp_to_dsuserid(lchip, ds_userid, userid_bmp);
    pe->u.temp_entry->temp_ad.com.u4_type = fwd_u_type;
    pe->u.temp_entry->temp_ad.com.u5_type = logic_u_type;
    pe->u.temp_entry->temp_ad.com.u3_type = u3_type;
    pe->u.temp_entry->temp_ad.com.u2_type = u2_type;
    pe->u.temp_entry->temp_ad.com.u1_type = u1_type;
    pe->u.temp_entry->temp_ad.com.userid_bmp = userid_bmp;
    pe->u.temp_entry->temp_ad.com.fwd_bmp = fwd_bmp;
    sal_memcpy(pe->u.temp_entry->action, temp_ds_userid, sizeof(pe->u.temp_entry->action));
    return CTC_E_NONE;
}

int32
sys_tmm_scl_get_field_action_userid(uint8 lchip, ctc_scl_field_action_t* p_action, void* pe_info)
{
    int32 ret = CTC_E_NONE;
    ds_t action_buffer = {0};
    void* p_action_buffer = action_buffer;
    uint32* temp_ds = NULL;
    ctc_scl_logic_port_t* p_logic_port = NULL;
    ctc_scl_aps_t* aps = NULL;
    ctc_scl_qos_map_t* p_qos = NULL;
    ctc_scl_vlan_edit_t* vlan_edit = NULL;
    ctc_scl_bind_t* bind = NULL;
    sys_scl_dot1br_t* p_dot1br = NULL;
    ctc_scl_force_decap_t* p_decap = NULL;
    ctc_scl_snooping_parser_t* p_snooping_parser = NULL;
    ctc_acl_log_t* p_acl_log = NULL;
    sys_scl_sw_entry_t* pe = (sys_scl_sw_entry_t*)pe_info;
    ctc_security_hmac_t hmac;
    uint8 is_discard= 0;
    uint8 is_to_cpu = 0;
    uint16 destmap = 0;
    uint16 gchip = 0;
    uint16 lport = 0;
    uint32 value = 0;
    uint32 bind_data[2] = {0};
    uint16 tmp_data = 0;
    /*uint8  tmp_data = 0;*/

    sal_memcpy(action_buffer, pe->u.temp_entry->action, sizeof(ds_t ));
    sys_tmm_scl_move_dsuserid_to_temp(lchip, p_action_buffer, pe->u.temp_entry->temp_ad.com.userid_bmp);

    switch(p_action->type)
    {
        case SYS_SCL_FIELD_ACTION_TYPE_IS_HALF:
        case CTC_SCL_FIELD_ACTION_TYPE_SERVICE_ACL_EN:
        case CTC_SCL_FIELD_ACTION_TYPE_SPAN_FLOW:
        case CTC_SCL_FIELD_ACTION_TYPE_COPY_TO_CPU:
        case CTC_SCL_FIELD_ACTION_TYPE_DENY_BRIDGE:
        case CTC_SCL_FIELD_ACTION_TYPE_ETREE_LEAF:
        case CTC_SCL_FIELD_ACTION_TYPE_LOGIC_PORT_SECURITY_EN:
        case SYS_SCL_FIELD_ACTION_TYPE_VPLS:
        case SYS_SCL_FIELD_ACTION_TYPE_VPWS:
        case CTC_SCL_FIELD_ACTION_TYPE_IGMP_SNOOP_EN:
             break;
        case CTC_SCL_FIELD_ACTION_TYPE_XDATA:
        {
            uint32 xdata[3] = {0};
            ctc_xdata_t* p_xdata = p_action->ext_data;
            
            CTC_PTR_VALID_CHECK(p_action->ext_data);
            CTC_ERROR_RETURN(DRV_FROM_AT(lchip)? CTC_E_NONE: CTC_E_NOT_SUPPORT);
            
            p_xdata->prof_id = GetDsUserId(V, xAdIndex_f, p_action_buffer);
            p_xdata->type = CTC_XDATA_PROF_TYPE_DSSCL;
            GetDsUserId(A, xAdData_f, p_action_buffer, xdata);
            xdata[1] = xdata[1] & 0x7FFFFFFF;
            if(GetDsUserId(V, xAdEn_f, p_action_buffer) && CTC_E_NONE == (MCHIP_XDATA(lchip)->prof_get_info(lchip, p_xdata, FALSE)))
            {
                uint8 loop = 0;
                ctc_xdata_field_t* p_field = NULL;
                for(loop = 0; loop<p_xdata->num; loop++)
                {
                    p_field = p_xdata->fields+loop;
                    if(!CTC_FLAG_ISSET(p_field->flag, CTC_XDATA_FIELD_FLAG_UDF))
                    {
                        SYS_USW_GET_XDATA(p_field->width, p_field->offset, p_field->data, xdata);
                    }
                    else
                    {
                        switch(p_field->offset)
                        {
                        case 0:
                            p_field->data = 2;
                            break;
                        case 16:
                            p_field->data = 3;
                            break;
                        case 32:
                            p_field->data = 1;
                            break;
                        case 48:
                            p_field->data = 0;
                            break;
                        }
                    }
                }
            }
            break;
        }
        case CTC_SCL_FIELD_ACTION_TYPE_DISCARD:
            if ( SYS_SCL_FWD_DISCARD != pe->u.temp_entry->temp_ad.fwd_type)
            {
                return CTC_E_NOT_EXIST;
            }
            
            break;
         case CTC_SCL_FIELD_ACTION_TYPE_DOT1AE_CHAN_ID:
             if (DRV_FROM_AT(lchip))
             {
                 return CTC_E_NOT_SUPPORT;
             }
            temp_ds = SYS_SCL_TEMP_USERID(p_action_buffer, SYS_SCL_USERID_BMP_FWD);
            p_action->data1 = GetTempDsFwdInfo(V, u_g2_ecmpGroupId_f, temp_ds)>>8;
            break;

        case CTC_SCL_FIELD_ACTION_TYPE_EFD:
            p_action->data0 = GetDsUserId(V, u3_g2_efdAction_f, p_action_buffer);
            break;
        case CTC_SCL_FIELD_ACTION_TYPE_PTP_CLOCK_ID:
            p_action->data0 = GetDsUserId(V, u3_g2_ptpIndex_f, p_action_buffer);
            break;
        case CTC_SCL_FIELD_ACTION_TYPE_FLOW_LKUP_BY_OUTER_HEAD:
            if (pe->u.temp_entry->temp_ad.com.u3_type == SYS_AD_UNION_G_2)
            {
                p_action->data0 = GetDsUserId(V, u3_g2_aclQosUseOuterInfo_f, p_action_buffer);
            }
            else if (pe->u.temp_entry->temp_ad.com.u1_type == SYS_AD_UNION_G_1)
            {
                p_action->data0 = GetDsUserId(V, u1_g1_aclQosUseOuterInfo_f, p_action_buffer);
            }
            break;
        case CTC_SCL_FIELD_ACTION_TYPE_IPFIX_LKUP_BY_OUTER_HEAD:
            if (pe->u.temp_entry->temp_ad.com.u3_type == SYS_AD_UNION_G_2)
            {
                p_action->data0 = GetDsUserId(V, u3_g2_ipfixUseOuterInfo_f, p_action_buffer);
            }
            else if (pe->u.temp_entry->temp_ad.com.u1_type == SYS_AD_UNION_G_1)
            {
                p_action->data0 = GetDsUserId(V, u1_g1_ipfixUseOuterInfo_f, p_action_buffer);
            }
            break;
        case CTC_SCL_FIELD_ACTION_TYPE_MAC_LIMIT :
            temp_ds = SYS_SCL_TEMP_USERID(p_action_buffer, SYS_SCL_USERID_BMP_LOGIC_PORT);
            is_discard = GetTempDsLogicPort(V, logicPortMacSecurityDiscard_f, temp_ds);
            is_to_cpu = is_discard && GetTempDsLogicPort(V, logicPortSecurityExceptionEn_f, temp_ds);
            p_action->data0= (is_to_cpu? CTC_MACLIMIT_ACTION_TOCPU: (is_discard? CTC_MACLIMIT_ACTION_DISCARD: CTC_MACLIMIT_ACTION_NONE));
            break;
        case CTC_SCL_FIELD_ACTION_TYPE_ROUTER_MAC_MATCH :
            temp_ds = SYS_SCL_TEMP_USERID(p_action_buffer, SYS_SCL_USERID_BMP_PORT_EXTENDER);
            p_action->data0 = CTC_IS_BIT_SET(temp_ds[1], SYS_SCL_USERID_ROUTER_MAC_HIT_BASE) && GetDsRouterMacTcamAd(V, isRouterMac_f, &temp_ds[1]);
            break;
        case CTC_SCL_FIELD_ACTION_TYPE_LOGIC_PORT:
            CTC_PTR_VALID_CHECK(p_action->ext_data);
            temp_ds = SYS_SCL_TEMP_USERID(p_action_buffer, SYS_SCL_USERID_BMP_LOGIC_PORT);
            p_logic_port = p_action->ext_data;
            p_logic_port->logic_port = GetTempDsLogicPort(V, logicSrcPort_f, temp_ds);
            p_logic_port->logic_port_type = GetTempDsLogicPort(V, logicSrcPortType_f, temp_ds);
            break;
        case CTC_SCL_FIELD_ACTION_TYPE_LOGIC_PORT_TYPE:
            temp_ds = SYS_SCL_TEMP_USERID(p_action_buffer, SYS_SCL_USERID_BMP_LOGIC_PORT);
            p_action->data0 = GetTempDsLogicPort(V, logicSrcPortType_f, temp_ds);
            break;
        case CTC_SCL_FIELD_ACTION_TYPE_STP_ID:
            p_action->data0 = GetDsUserId(V, u1_g1_stpId_f, p_action_buffer);
            p_action->data1 = GetDsUserId(V, u1_g1_stpIdValid_f, p_action_buffer);
            break;
        case CTC_SCL_FIELD_ACTION_TYPE_APS:
            CTC_PTR_VALID_CHECK(p_action->ext_data);
            aps = p_action->ext_data;
            temp_ds = SYS_SCL_TEMP_USERID(p_action_buffer, SYS_SCL_USERID_BMP_LOGIC_PORT);
            aps->protected_vlan = GetTempDsLogicPort(V, vsiIdOrUserVlanPtr_f, temp_ds) & MCHIP_CAP(SYS_CAP_MAX_VLAN_PTR);
            temp_ds = SYS_SCL_TEMP_USERID(p_action_buffer, SYS_SCL_USERID_BMP_FWD);
            aps->is_working_path = !GetTempDsFwdInfo(V, u_g1_apsSelectProtectingPath_f, temp_ds);
            aps->protected_vlan_valid = !!(aps->protected_vlan);
            aps->aps_select_group_id = GetTempDsFwdInfo(V, u_g1_apsSelectGroupId_f, temp_ds);
            break;
        case CTC_SCL_FIELD_ACTION_TYPE_REDIRECT:
            if ( SYS_SCL_FWD_REDIRECT != pe->u.temp_entry->temp_ad.fwd_type)
            {
                return CTC_E_NOT_EXIST;
            }
            p_action->data0 = pe->u.temp_entry->temp_ad.nexthop_id;
            break;
        case CTC_SCL_FIELD_ACTION_TYPE_REDIRECT_PORT:   /* only merge dsfwd support? */
            if ( SYS_SCL_FWD_REDIRECT_PORT != pe->u.temp_entry->temp_ad.fwd_type)
            {
                return CTC_E_NOT_EXIST;
            }
            temp_ds = SYS_SCL_TEMP_USERID(p_action_buffer, SYS_SCL_USERID_BMP_FWD);
            destmap = GetTempDsFwdInfo(V, u2_g2_adDestMap_f, temp_ds);
            gchip = SYS_DECODE_DESTMAP_GCHIP(destmap);
            lport = destmap & 0x1FF;
            p_action->data0 = SYS_MAP_DRV_LPORT_TO_CTC_GPORT(gchip, lport);
            break;
        case CTC_SCL_FIELD_ACTION_TYPE_POLICER_ID:
            p_action->data0 = GetDsUserId(V, policerPtr_f, p_action_buffer)&0x0FFFF; 
            p_action->data1 = pe->u.temp_entry->temp_ad.is_service_policer;
            break;
        case CTC_SCL_FIELD_ACTION_TYPE_COS_HBWP_POLICER:
            p_action->data0 = GetDsUserId(V, policerPtr_f, p_action_buffer)&0x0FFFF; 
            break;
        case CTC_SCL_FIELD_ACTION_TYPE_SERVICE_ID:
            p_action->data0 = GetDsUserId(V, u2_g1_serviceId_f, p_action_buffer);
            break;
        case CTC_SCL_FIELD_ACTION_TYPE_STATS:
            {
                uint32 statsptr = 0;
                statsptr = GetDsUserId(V, statsPtr_f, p_action_buffer);
                p_action->data0 = 0;
                /* no need error return*/
                sys_usw_flow_stats_lookup_statsid(lchip, CTC_STATS_STATSID_TYPE_SCL, statsptr, &p_action->data0, CTC_INGRESS);
            }
            break;
        case CTC_SCL_FIELD_ACTION_TYPE_QOS_MAP:
            CTC_PTR_VALID_CHECK(p_action->ext_data);
            p_qos = (ctc_scl_qos_map_t*)(p_action->ext_data);
            temp_ds = SYS_SCL_TEMP_USERID(p_action_buffer, SYS_SCL_USERID_BMP_LOGIC_PORT);
            if(!GetTempDsLogicPort(V, uType_f, temp_ds) && GetTempDsLogicPort(V, u_g1_userPrioValid_f, temp_ds))
            {
                p_qos->priority = GetTempDsLogicPort(V, u_g1_userPrio_f, temp_ds);
                p_qos->color = GetTempDsLogicPort(V, u_g1_userColor_f, temp_ds);
                CTC_SET_FLAG(p_qos->flag, CTC_SCL_QOS_MAP_FLAG_PRIORITY_VALID);
            }
            else if (!GetTempDsLogicPort(V, uType_f, temp_ds))
            {
                p_qos->color = GetTempDsLogicPort(V, u_g1_userColor_f, temp_ds);
            }
            else
            {
                p_qos->trust_dscp = GetTempDsLogicPort(V, u_g2_trustDscp_f, temp_ds);
                p_qos->dscp_domain = GetTempDsLogicPort(V, u_g2_dscpPhbPtr_f, temp_ds);
                p_qos->cos_domain = GetTempDsLogicPort(V, u_g2_cosPhbPtr_f, temp_ds);
                if(GetTempDsLogicPort(V, u_g2_cosPhbUseInnerValid_f, temp_ds))
                {
                    p_qos->trust_cos = GetTempDsLogicPort(V, u_g2_cosPhbUseInner_f, temp_ds);
                    CTC_SET_FLAG(p_qos->flag, CTC_SCL_QOS_MAP_FLAG_TRUST_COS_VALID);
                }
            }
            if(GetDsUserId(V, u2Type_f, p_action_buffer)==3 && GetDsUserId(V, u2_g4_newDscpValid_f, p_action_buffer))
            {
                p_qos->dscp = GetDsUserId(V, u2_g4_newDscp_f, p_action_buffer);
                CTC_SET_FLAG(p_qos->flag, CTC_SCL_QOS_MAP_FLAG_DSCP_VALID);
            }
            break;
        case CTC_SCL_FIELD_ACTION_TYPE_SRC_CID:
        case CTC_SCL_FIELD_ACTION_TYPE_DST_CID:
            p_action->data0 = GetDsUserId(V, u2_g2_categoryId_f, p_action_buffer);
            break;

        case CTC_SCL_FIELD_ACTION_TYPE_VLAN_EDIT:
        {
            CTC_PTR_VALID_CHECK(p_action->ext_data);
            vlan_edit = (ctc_scl_vlan_edit_t*)(p_action->ext_data);
            if (!pe->u.temp_entry->temp_ad.vlan_edit)
            {
                SYS_SCL_DBG_OUT(CTC_DEBUG_LEVEL_ERROR, " Entry not found \n");
                CTC_ERROR_RETURN(CTC_E_NOT_EXIST);
            }
            CTC_ERROR_RETURN(sys_usw_scl_unmapping_vlan_edit(lchip, vlan_edit, &pe->u.temp_entry->temp_ad.vlan_edit->action_profile));

            temp_ds = SYS_SCL_TEMP_USERID(p_action_buffer, SYS_SCL_USERID_BMP_VLAN_XLATE);
            /* refer to ctc_vlan_tag_sl_t, only CTC_VLAN_TAG_SL_NEW need to write hw table */
            if (CTC_VLAN_TAG_SL_NEW == vlan_edit->ccfi_sl)
            {
                vlan_edit->ccfi_new = GetTempDsVlanXlate(V, userCcfi_f, temp_ds);
            }
            if (CTC_VLAN_TAG_SL_NEW == vlan_edit->ccos_sl)
            {
                vlan_edit->ccos_new = GetTempDsVlanXlate(V, userCcos_f, temp_ds);
            }
            if (CTC_VLAN_TAG_SL_NEW == vlan_edit->cvid_sl)
            {
                vlan_edit->cvid_new = GetTempDsVlanXlate(V, userCvlanId_f, temp_ds);
            }
            if (CTC_VLAN_TAG_SL_NEW == vlan_edit->scfi_sl)
            {
                vlan_edit->scfi_new = GetTempDsVlanXlate(V, userScfi_f, temp_ds);
            }
            if (CTC_VLAN_TAG_SL_NEW == vlan_edit->scos_sl)
            {
                vlan_edit->scos_new = GetTempDsVlanXlate(V, userScos_f, temp_ds);
            }
            if (CTC_VLAN_TAG_SL_NEW == vlan_edit->svid_sl)
            {
                vlan_edit->svid_new = GetTempDsVlanXlate(V, userSvlanId_f, temp_ds);
            }
            /*recovery CTC_VLAN_TAG_OP_VALID*/
            if( GetDsUserId(V, vlanActionProfileValid_f, p_action_buffer) && \
                GetDsUserId(V, svlanTagOperationValid_f, p_action_buffer) && \
                !vlan_edit->stag_op)
            {
                vlan_edit->stag_op = CTC_VLAN_TAG_OP_VALID;
            }
            if( GetDsUserId(V, vlanActionProfileValid_f, p_action_buffer) && \
                GetDsUserId(V, cvlanTagOperationValid_f, p_action_buffer) && \
                !vlan_edit->ctag_op)
            {
                vlan_edit->ctag_op = CTC_VLAN_TAG_OP_VALID;
            }
            break;
        }
        case CTC_SCL_FIELD_ACTION_TYPE_FID:
            temp_ds = SYS_SCL_TEMP_USERID(p_action_buffer, SYS_SCL_USERID_BMP_FWD);
            if(GetTempDsFwdInfo(V, u_g4_vsiIdValid_f, temp_ds))
            {
                p_action->data0 = GetTempDsFwdInfo(V, u_g4_fid_f, temp_ds);
            }
            break;
        case CTC_SCL_FIELD_ACTION_TYPE_VRFID:
            temp_ds = SYS_SCL_TEMP_USERID(p_action_buffer, SYS_SCL_USERID_BMP_FWD);
            if (pe->u.temp_entry->temp_ad.com.fwd_bmp == 1 || pe->u.temp_entry->temp_ad.com.fwd_bmp == 5)
            {
                p_action->data0 = GetTempDsFwdInfo(V, u_g4_fid_f, temp_ds);
            }
            else if (pe->u.temp_entry->temp_ad.com.fwd_bmp == 3)
            {
                p_action->data0 = GetTempDsFwdInfo(V, u2_g1_dsFwdPtr_f, temp_ds);
            }
            break;
        case SYS_SCL_FIELD_ACTION_TYPE_VN_ID:
        {
            uint32 vn_id = 0;
            uint16 fid = 0;
            temp_ds = SYS_SCL_TEMP_USERID(p_action_buffer, SYS_SCL_USERID_BMP_FWD);
            if(GetTempDsFwdInfo(V, u_g4_vsiIdValid_f, temp_ds))
            {
                fid =  GetTempDsFwdInfo(V, u_g4_fid_f, temp_ds);
                sys_usw_vlan_overlay_get_vn_id(lchip,fid,&vn_id);
                p_action->data0 = vn_id;
            }
        }
            break;
        case CTC_SCL_FIELD_ACTION_TYPE_BINDING_EN:
            CTC_PTR_VALID_CHECK(p_action->ext_data);
            bind = p_action->ext_data;
            temp_ds = SYS_SCL_TEMP_USERID(p_action_buffer, SYS_SCL_USERID_BMP_BINDING);
            GetTempDsBinding(A, bindingData_f, temp_ds, bind_data);
            if (GetTempDsBinding(V, bindingMacSa_f, temp_ds))
            {
                bind->type = CTC_SCL_BIND_TYPE_MACSA;
                SYS_USW_SET_USER_MAC(bind->mac_sa, bind_data);
            }
            else if (bind_data[0] == 0)
            {
                bind->type = CTC_SCL_BIND_TYPE_PORT;
                bind->gport = SYS_MAP_DRV_GPORT_TO_CTC_GPORT(bind_data[1]);
            }
            else if (bind_data[0] == 1)
            {
                bind->type = CTC_SCL_BIND_TYPE_VLAN;
                bind->vlan_id = (bind_data[1]>>4)&0xFFFF;
            }
            else if ((bind_data[0]&0xF) == 2)
            {
                bind->type = CTC_SCL_BIND_TYPE_IPV4SA;
                bind->ipv4_sa = ((bind_data[1]&0xF)<< 28) | (bind_data[0]>>4);
            }
            else if ((bind_data[0]&0xF) == 3)
            {
                bind->type = CTC_SCL_BIND_TYPE_IPV4SA_VLAN;
                bind->vlan_id = bind_data[1]>>4;
                bind->ipv4_sa = ((bind_data[1]&0xF) << 28) | (bind_data[0]>>4);
            }
            break;
        case CTC_SCL_FIELD_ACTION_TYPE_OAM:
            temp_ds = SYS_SCL_TEMP_USERID(p_action_buffer, SYS_SCL_USERID_BMP_FWD);
            if (CTC_BMP_ISSET(pe->action_bmp, CTC_SCL_FIELD_ACTION_TYPE_FID) && 3 == GetTempDsFwdInfo(V, uType_f, temp_ds) && GetTempDsFwdInfo(V, u_g4_vsiIdValid_f, temp_ds))
            {
                /* vpls */
                p_action->data1 = GetTempDsFwdInfo(V, u_g4_fid_f, temp_ds);
            }
            else
            {
                /* vpws */
                temp_ds = SYS_SCL_TEMP_USERID(p_action_buffer, SYS_SCL_USERID_BMP_LOGIC_PORT);
                if (GetTempDsLogicPort(V, vsiIdValid_f, temp_ds))
                {
                    p_action->data1 = GetTempDsLogicPort(V, vsiIdOrUserVlanPtr_f, temp_ds);
                    p_action->data1 -= (1 << 13);
                }
            }
            break;
        case SYS_SCL_FIELD_ACTION_TYPE_DOT1BR_PE:
            CTC_PTR_VALID_CHECK(p_action->ext_data);
            p_dot1br = (sys_scl_dot1br_t*) p_action->ext_data;
            temp_ds = SYS_SCL_TEMP_USERID(p_action_buffer, SYS_SCL_USERID_BMP_PORT_EXTENDER);
            p_dot1br->lport_valid =GetTempDsPortExtender(V, localPhyPortValid_f, temp_ds);
            p_dot1br->lport = GetTempDsPortExtender(V, localPhyPort_f, temp_ds);
            p_dot1br->src_gport_valid = GetTempDsPortExtender(V, globalSrcPortValid_f, temp_ds);
            p_dot1br->src_gport = SYS_MAP_DRV_GPORT_TO_CTC_GPORT(GetTempDsPortExtender(V, globalSrcPort_f, temp_ds));
            temp_ds = SYS_SCL_TEMP_USERID(p_action_buffer, SYS_SCL_USERID_BMP_FLOW);
            p_dot1br->src_discard = GetTempDsFlow(V, discard_f, temp_ds);
            p_dot1br->exception_en = GetTempDsFlow(V, exceptionEn_f, temp_ds);
            p_dot1br->bypass_all = GetDsUserId(V, bypassAll_f, p_action_buffer);
            break;
        case CTC_SCL_FIELD_ACTION_TYPE_FLEX_EDIT:
        {
            uint8 flex_valid = 0;
            ctc_scl_flex_edit_t* flex_edit = NULL;
            CTC_PTR_VALID_CHECK(p_action->ext_data);
            flex_edit = (ctc_scl_flex_edit_t*)p_action->ext_data;
            temp_ds = SYS_SCL_TEMP_USERID(p_action_buffer, SYS_SCL_USERID_BMP_FLOW);
            flex_valid = GetTempDsFlow(V, flexOpValid_f, temp_ds);
            if (flex_valid)
            {
                flex_edit->start_offset = ((GetTempDsFlow(V, startOffsetUdfSel_f, temp_ds)& 0x3) << 6);
                flex_edit->start_offset |= GetTempDsFlow(V, routerMacProfileId_f, temp_ds);
                flex_edit->len = ((GetTempDsFlow(V, payloadOffsetUdfSel_f, temp_ds)& 0x3) << 6);
                flex_edit->len |= GetTempDsFlow(V, payloadOffset_f, temp_ds);
                flex_edit->start_offset_type = (GetTempDsFlow(V, hashBulkBitmapProfile_f, temp_ds) & 0x3) - 1;
            }
            break;
        }
        case SYS_SCL_FIELD_ACTION_TYPE_SRV6:
            {
                uint8 flex_valid = 0;
                sys_scl_srv6_t* srv6 = NULL;
                CTC_PTR_VALID_CHECK(p_action->ext_data);
                srv6 = (sys_scl_srv6_t*)p_action->ext_data;
                temp_ds = SYS_SCL_TEMP_USERID(p_action_buffer, SYS_SCL_USERID_BMP_FLOW);
                flex_valid = GetTempDsFlow(V, flexOpValid_f, temp_ds);
                if (!flex_valid)
                {
                    srv6->router_mac_profile = GetTempDsFlow(V, routerMacProfileId_f, temp_ds);
                }
                break;
            }
        case CTC_SCL_FIELD_ACTION_TYPE_CANCEL_LKUP_BMP:
            {
                uint8 scl_id = (pe->is_default) ? p_action->data1: pe->group_priority;
                uint8 hi_bits = 0;
                uint8 lo_bits = 0;
                uint8 clear_bmp = 0;
                uint8 mask_array[4] = {0,0x01,0x03,0x07};

                clear_bmp = GetDsUserId(V, clearSclRsltBmp_f, p_action_buffer);
                hi_bits = (clear_bmp >> scl_id);
                lo_bits = clear_bmp & mask_array[scl_id];
                p_action->data0 = (hi_bits << (scl_id + 1)) | lo_bits;
                break;
            }
        case CTC_SCL_FIELD_ACTION_TYPE_USER_VLANPTR:
            temp_ds = SYS_SCL_TEMP_USERID(p_action_buffer, SYS_SCL_USERID_BMP_LOGIC_PORT);
            p_action->data0 = GetTempDsLogicPort(V, vsiIdOrUserVlanPtr_f, temp_ds) & MCHIP_CAP(SYS_CAP_MAX_VLAN_PTR);
            break;
        case CTC_SCL_FIELD_ACTION_TYPE_METADATA:
#if 0
            tmp_data = GetDsUserId(V, u2_g2_categoryType_f, p_action_buffer);
            tmp_data = (tmp_data<<1) | ((GetDsUserId(V, u2_g2_categoryId_f, p_action_buffer)>>15) & 0x1);
            if (tmp_data == CTC_METADATA_TYPE_METADATA)
            {
                p_action->data0 = GetDsUserId(V,  u2_g2_categoryId_f, p_action_buffer) & 0x7FFF;
            }
            else
            {
                SYS_SCL_DBG_OUT(CTC_DEBUG_LEVEL_ERROR, " Entry not found \n");
                CTC_ERROR_RETURN(CTC_E_NOT_EXIST);
            }
#endif
            tmp_data = GetDsUserId(V, u2_g2_categoryType_f, p_action_buffer);
            tmp_data = (tmp_data<<1) | ((GetDsUserId(V, u2_g2_categoryId_f, p_action_buffer)>>15) & 0x1);
            if (pe->u.temp_entry->temp_ad.com.u2_type == SYS_AD_UNION_G_2 && tmp_data == CTC_METADATA_TYPE_METADATA)
            {
                p_action->data0 = GetDsUserId(V, u2_g2_categoryId_f, p_action_buffer) &0x7FFF;
            }
            else if(pe->u.temp_entry->temp_ad.com.u1_type == SYS_AD_UNION_G_1)
            {
               if (GetDsUserId(V, u1Type_f, p_action_buffer)!=0)
                {
                    SYS_SCL_DBG_OUT(CTC_DEBUG_LEVEL_ERROR, " Entry not found \n");
                    CTC_ERROR_RETURN(CTC_E_NOT_EXIST);
                }
                p_action->data0 = GetDsUserId(V, u1_g1_metadata_f, p_action_buffer);
            }

            
            break;
        case CTC_SCL_FIELD_ACTION_TYPE_FORCE_BRIDGE:
        case CTC_SCL_FIELD_ACTION_TYPE_FORCE_LEARNING:
        case CTC_SCL_FIELD_ACTION_TYPE_FORCE_ROUTE:
        case CTC_SCL_FIELD_ACTION_TYPE_DENY_LEARNING:
        case CTC_SCL_FIELD_ACTION_TYPE_DENY_ROUTE:
            break;
        case CTC_SCL_FIELD_ACTION_TYPE_LB_HASH_SELECT_ID:
            temp_ds = SYS_SCL_TEMP_USERID(p_action_buffer, SYS_SCL_USERID_BMP_FLOW);
            p_action->data0 = GetTempDsFlow(V, hashBulkBitmapProfile_f, temp_ds);
            break;
        case CTC_SCL_FIELD_ACTION_TYPE_FORCE_DECAP:
            CTC_PTR_VALID_CHECK(p_action->ext_data);
            p_decap = (ctc_scl_force_decap_t*)(p_action->ext_data);
            temp_ds = SYS_SCL_TEMP_USERID(p_action_buffer, SYS_SCL_USERID_BMP_FLOW);
            p_decap->force_decap_en = GetTempDsFlow(V, innerPacketLookup_f, temp_ds);
            p_decap->offset_base_type = GetTempDsFlow(V, payloadOffsetStartPoint_f, temp_ds) - 1;
            p_decap->ext_offset = GetTempDsFlow(V, payloadOffset_f, temp_ds);
            p_decap->payload_type = GetTempDsFlow(V, packetType_f, temp_ds);
            p_decap->use_outer_ttl = GetTempDsFlow(V, ttlUpdate_f, temp_ds)? 0: 1;
            break;
        case CTC_SCL_FIELD_ACTION_TYPE_SNOOPING_PARSER:
            CTC_PTR_VALID_CHECK(p_action->ext_data);
            p_snooping_parser = (ctc_scl_snooping_parser_t*)(p_action->ext_data);
            temp_ds = SYS_SCL_TEMP_USERID(p_action_buffer, SYS_SCL_USERID_BMP_FLOW);
            p_snooping_parser->enable = GetTempDsFlow(V, forceSecondParser_f, temp_ds);
            p_snooping_parser->start_offset_type = GetTempDsFlow(V, payloadOffsetStartPoint_f, temp_ds) - 1;
            p_snooping_parser->ext_offset = GetTempDsFlow(V, payloadOffset_f, temp_ds);
            p_snooping_parser->payload_type = GetTempDsFlow(V, packetType_f, temp_ds);
            p_snooping_parser->use_inner_hash_en = GetTempDsFlow(V, forceUseInnerDoHash_f, temp_ds);
            break;
        case CTC_SCL_FIELD_ACTION_TYPE_HMAC_ID:
            if ((DRV_IS_TMM(lchip) || DRV_IS_TMG(lchip)) && GetDsUserId(V, u1_g1_metadataTypeExt_f, p_action_buffer))
            {
                value = GetDsUserId(V, u1_g1_metadata_f, p_action_buffer);
                CTC_BIT_UNSET(value, 15);
            }
            else
            {
                SYS_SCL_DBG_OUT(CTC_DEBUG_LEVEL_ERROR, " Entry not found \n");
                CTC_ERROR_RETURN(CTC_E_NOT_EXIST);
            }
            sal_memset(&hmac, 0, sizeof(ctc_security_hmac_t));
            CTC_ERROR_RETURN(SYS_CB(SYS_CB_HMAC_GET_SHA_KEY, lchip, &hmac, &value, 1));
            p_action->data0 = hmac.hmac_id;
            break;
        case CTC_SCL_FIELD_ACTION_TYPE_RANDOM_LOG:
            CTC_PTR_VALID_CHECK(p_action->ext_data);
            p_acl_log = (ctc_acl_log_t*)p_action->ext_data;
            if (pe->u.temp_entry->temp_ad.com.u3_type == SYS_AD_UNION_G_2)
            {
                p_acl_log->log_id = GetDsUserId(V, u3_g2_aclLogLevel_f, p_action_buffer);
                p_acl_log->session_id = GetDsUserId(V, u3_g2_aclLogId_f, p_action_buffer);
                p_acl_log->percent = GetDsUserId(V, u3_g2_randomThresholdShift_f, p_action_buffer);
            }
            else
            {
                p_acl_log->log_id = GetDsUserId(V, u2_g4_aclLogLevel_f, p_action_buffer);
                p_acl_log->session_id = GetDsUserId(V, u2_g4_aclLogId_f, p_action_buffer);
                p_acl_log->percent = GetDsUserId(V, u2_g4_randomThresholdShift_f, p_action_buffer);
            }
            break;
        case CTC_SCL_FIELD_ACTION_TYPE_ARP_ACTION:
            if (GetDsUserId(V, u1_g1_arpCtlEn_f, p_action_buffer))
            {
                p_action->data0 = GetDsUserId(V, u1_g1_arpExceptionType_f, p_action_buffer);
            }
            break;

        case CTC_SCL_FIELD_ACTION_TYPE_IPV4_BASED_L2MC :
            if (GetDsUserId(V, u1_g1_forceIpv4LookupEn_f, p_action_buffer))
            {
                p_action->data0 = GetDsUserId(V, u1_g1_forceIpv4Lookup_f, p_action_buffer);
            }
            break;
        case CTC_SCL_FIELD_ACTION_TYPE_IPV6_BASED_L2MC :
            if (GetDsUserId(V, u1_g1_forceIpv6LookupEn_f, p_action_buffer))
            {
                p_action->data0 = GetDsUserId(V, u1_g1_forceIpv6Lookup_f, p_action_buffer);
            }
            break;
        /*
        case CTC_SCL_FIELD_ACTION_TYPE_OAM_TUNNEL_EN:
            break;
        */
        case CTC_SCL_FIELD_ACTION_TYPE_UDF_ID:
            value = GetDsUserId(V, u2_g1_udfHitIndex_f, p_action_buffer); /* flow udf ad index */
            ret = sys_usw_acl_get_flow_udf_id_by_adindex(lchip, value, &p_action->data0);
            if (ret)
            {
                return CTC_E_NOT_EXIST;
            }
            break;
        case CTC_SCL_FIELD_ACTION_TYPE_LOCAL_ARP:
            p_action->data0 = GetDsUserId(V, u2_g4_arpTargetIpIsLocal_f, p_action_buffer);
            break;
        case CTC_SCL_FIELD_ACTION_TYPE_ISOLATION_ID:
            if (CTC_BMP_ISSET(pe->action_bmp, CTC_SCL_FIELD_ACTION_TYPE_ISOLATION_ID))
            {
                p_action->data0 = GetDsUserId(V, u3_g2_aclLogLevel_f, p_action_buffer) << 4;
                p_action->data0 |= GetDsUserId(V, u3_g2_randomThresholdShift_f, p_action_buffer);
            }
            break;
        case CTC_SCL_FIELD_ACTION_TYPE_L3IF_PROPERTY:
            {
                mac_addr_t* mac;
                CTC_PTR_VALID_CHECK(p_action->ext_data);
                mac = (mac_addr_t*)p_action->ext_data;
                p_action->data0 = CTC_L3IF_PROP_ROUTE_MAC_LOW_8BITS;
                sys_usw_l3if_get_inner_router_mac(lchip, pe->u.temp_entry->temp_ad.inner_rmac_index, mac);
                break;
            }
        case CTC_SCL_FIELD_ACTION_TYPE_CHANGE_LKUP_PRI:
            p_action->data0 = GetDsUserId(V, clearSclRsltBmp_f, p_action_buffer);
            break;
        default:
            SYS_SCL_DBG_OUT(CTC_DEBUG_LEVEL_ERROR, " API or some feature is not supported \n");
            CTC_ERROR_RETURN(CTC_E_NOT_EXIST);

    }
    return CTC_E_NONE;
}

int32
sys_tmm_scl_update_action(uint8 lchip, void* data, void* change_nh_param)
{
    sys_scl_sw_entry_t* pe = (sys_scl_sw_entry_t*)data;
    sys_nh_info_dsnh_t* p_dsnh_info = change_nh_param;
    uint32* temp_ds = NULL;
    ds_t   action;
    uint32 cmdr  = 0;
    uint32 cmdw  = 0;
    uint32 fwd_offset = 0;
    uint32 key_id = 0;
    uint32 act_id = 0;
    uint32 hw_key_index = 0;
    uint32 hw_ad_index= 0;
    uint8  igs_hash_key = 0;
    uint8 ad_type = 0;
    uint8 scl_id = 0;
    uint8 size[SYS_SCL_SW_AD_TYPE_IGS_MAX] = {CTC_OFFSET_OF(sys_scl_sw_igs_ad0_t, calc_key_len),
                                           CTC_OFFSET_OF(sys_scl_sw_igs_ad1_t, calc_key_len),
                                           CTC_OFFSET_OF(sys_scl_sw_igs_ad2_t, calc_key_len),
                                           CTC_OFFSET_OF(sys_scl_sw_igs_ad3_t, calc_key_len),
                                           CTC_OFFSET_OF(sys_scl_sw_igs_ad_t, calc_key_len)};
    sys_scl_sw_igs_ad_t* p_ad = NULL;
    ds_t  new_profile;
    sys_scl_sw_igs_ad_t  old_profile;
    sys_scl_sw_igs_ad_t  temp_ad;
    sys_scl_sw_igs_ad_t* out_profile = NULL;
    ctc_field_key_t      field_key;
    int32 ret = 0;
    sys_scl_sw_temp_entry_t temp_entry;
    uint8 spool_upddate = 0;
    uint32 key_id1 = 0;
    uint32 act_id1 = 0;
    sys_scl_sw_entry_t* chk_pe = NULL;

    SYS_SCL_DBG_OUT(CTC_DEBUG_LEVEL_FUNC, "%s()\n", __FUNCTION__);
    sal_memset(&action, 0, sizeof(ds_t));
    sal_memset(&new_profile, 0, sizeof(sys_scl_sw_igs_ad_t));
    sal_memset(&field_key, 0, sizeof(ctc_field_key_t));
    sal_memset(&old_profile, 0, sizeof(sys_scl_sw_igs_ad_t));
    sal_memset(&temp_ad, 0, sizeof(sys_scl_sw_igs_ad_t));

    if (p_dsnh_info->need_lock)
    {
        SYS_SCL_DBG_OUT(CTC_DEBUG_LEVEL_INFO, "Add Lock\n");
        SYS_SCL_LOCK(lchip);
        
        _sys_usw_scl_get_nodes_by_eid(lchip, p_dsnh_info->chk_data, &chk_pe);
        if( chk_pe == NULL ||  pe != chk_pe )
        {
            ret = CTC_E_NONE;
            goto error0;
        }
    }

    igs_hash_key = !(SCL_ENTRY_IS_TCAM(pe->key_type) || pe->resolve_conflict) && (SYS_SCL_ACTION_EGRESS != pe->action_type);

    _sys_usw_scl_get_table_id(lchip, (SYS_SCL_IS_HASH_COM_MODE(pe)? 0: pe->group_priority), pe, &key_id, &act_id);
    if (SYS_SCL_IS_HASH_COM_MODE(pe))
    {
        _sys_usw_scl_get_table_id(lchip, 1, pe, &key_id1, &act_id1);
    }
    /* get key_index and ad_index */
    _sys_usw_scl_get_index(lchip, key_id, pe, &hw_key_index, &hw_ad_index);

    SYS_SCL_DBG_OUT(CTC_DEBUG_LEVEL_INFO, "update bind scl action, key_tbl_id:[%u]  ad_tbl_id:[%u]  ad_index:[%u]\n", key_id, act_id, hw_ad_index);

    cmdr = DRV_IOR(act_id, DRV_ENTRY_FLAG);
    cmdw = DRV_IOW(act_id, DRV_ENTRY_FLAG);

    if (!pe->is_buffer)
    {
        DRV_IOCTL(lchip, hw_ad_index, DRV_CMD_BMP_EN(cmdr, MCHIP_FEATURE_PP_EN(lchip,CTC_FEATURE_SCL)), &action);
        sys_tmm_scl_move_dsuserid_to_temp(lchip, &action, ((sys_scl_sw_igs_ad_t*)pe->u.ad)->com.userid_bmp);
        _sys_usw_scl_mapping_ad(pe->u.ad, &temp_ad, 1, igs_hash_key, pe->direction);
        p_ad = &temp_ad;
    }
    else
    {
        sal_memcpy(&action, &pe->u.temp_entry->action, sizeof(action));
        sys_tmm_scl_move_dsuserid_to_temp(lchip, &action, pe->u.temp_entry->temp_ad.com.userid_bmp);
        p_ad = &pe->u.temp_entry->temp_ad;
    }

    if (p_ad->nexthop_id != p_dsnh_info->nhid)
    {
        ret = CTC_E_NONE;
        goto error0;
    }

    temp_ds = SYS_SCL_TEMP_USERID(&action, SYS_SCL_USERID_BMP_FWD);

    if ((p_dsnh_info->merge_dsfwd == 2) || p_dsnh_info->cloud_sec_en)
    {
        if ((0 != GetTempDsFwdInfo(V, u2_g1_dsFwdPtr_f, temp_ds)) && (0 == GetTempDsFwdInfo(V, u2Type_f, temp_ds)))
        {
            ret = CTC_E_NONE;
            goto error0;
        }

        /*1. alloc dsfwd*/
        CTC_ERROR_GOTO(sys_usw_nh_get_dsfwd_offset(lchip, p_ad->nexthop_id, &fwd_offset, 0, CTC_FEATURE_SCL), ret, error0);

        /*confirm if cb twice or not*/

        /*clear u_g3*/
        SetTempDsFwdInfo(V, u_g3_adNextHopExt_f, temp_ds, 0);
        SetTempDsFwdInfo(V, u_g3_adNextHopPtr_f, temp_ds, 0);
        SetTempDsFwdInfo(V, uType_f, temp_ds, 0);
        /*clear u2_g2*/
        SetTempDsFwdInfo(V, u2_g2_adApsBridgeEn_f, temp_ds, 0);
        SetTempDsFwdInfo(V, u2_g2_adDestMap_f, temp_ds, 0);
        SetTempDsFwdInfo(V, u2_g2_bypassIngressEdit_f, temp_ds, 0);
        SetTempDsFwdInfo(V, u2Type_f, temp_ds, 0);
        /*2. update ad*/
        SetTempDsFwdInfo(V, u2_g1_dsFwdPtr_f, temp_ds, fwd_offset);

        p_ad->bind_nh = 0;
        p_ad->com.u4_type = SYS_AD_UNION_G_NA;
    }
    else
    {
        if((0 != GetTempDsFwdInfo(V, u2_g1_dsFwdPtr_f, temp_ds)) && (0 == GetTempDsFwdInfo(V, u2Type_f, temp_ds)))
        {
             ret = CTC_E_NONE;
             goto error0;
        }

        SetTempDsFwdInfo(V, u2_g2_adDestMap_f, temp_ds, p_dsnh_info->dest_map);
        SetTempDsFwdInfo(V, u2_g2_adApsBridgeEn_f, temp_ds, p_dsnh_info->aps_en);
        SetTempDsFwdInfo(V, u2_g2_bypassIngressEdit_f, temp_ds, p_dsnh_info->bypass_igr_edit);
        SetTempDsFwdInfo(V, u_g3_adNextHopPtr_f, temp_ds, p_dsnh_info->dsnh_offset);
        SetTempDsFwdInfo(V, u_g3_adNextHopExt_f, temp_ds, p_dsnh_info->nexthop_ext);
        SetTempDsFwdInfo(V, u2Type_f, temp_ds, 1);
        SetTempDsFwdInfo(V, uType_f, temp_ds, 2);
        p_ad->com.u4_type = SYS_AD_UNION_G_3;
    }

    _sys_tmm_scl_move_temp_to_dsuserid(lchip, &action, p_ad->com.userid_bmp);

    /*Update spool */
    if ((igs_hash_key) && (!pe->is_buffer))
    {
        scl_id = ((1 == MCHIP_CAP(SYS_CAP_SCL_HASH_NUM)||SYS_SCL_IS_HASH_COM_MODE(pe))? 0: pe->group_priority);
        if (scl_id > 1)
        {
            ret = CTC_E_INVALID_PARAM;
            goto error0;
        }
        if ((SYS_SCL_ACTION_INGRESS == pe->action_type) || (SYS_SCL_ACTION_TUNNEL ==  pe->action_type))
        {
            uint32 zeros[4] = {0};
            uint8 is_half = 0;
            is_half = !sal_memcmp((action + MCHIP_CAP(SYS_CAP_SCL_ACTION_SIZE) / 2), zeros, MCHIP_CAP(SYS_CAP_SCL_ACTION_SIZE) /2 * sizeof(uint32)) ? 1: 0;
            if(is_half != pe->is_half)
            {
                SetDsUserId(V, isHalf_f, &action, is_half);
                pe->is_half = is_half;
                CTC_ERROR_GOTO(_sys_usw_scl_get_table_id(lchip, (SYS_SCL_IS_HASH_COM_MODE(pe)? 0: pe->group_priority), pe, &key_id, &act_id), ret, error0);
                if (SYS_SCL_IS_HASH_COM_MODE(pe))
                {
                    _sys_usw_scl_get_table_id(lchip, 1, pe, &key_id1, &act_id1);
                }
                cmdw = DRV_IOW(act_id, DRV_ENTRY_FLAG);
            }
        }
        p_ad->com.is_half = pe->is_half;
        p_ad->action = &action;
        _sys_usw_scl_mapping_ad(&new_profile, p_ad, 0, igs_hash_key, CTC_INGRESS);
        ((sys_scl_sw_igs_ad_t*)(&new_profile))->com.priority = scl_id;
        ((sys_scl_sw_igs_ad_t*)(&new_profile))->com.ad_index = SYS_SCL_INVALID_AD_INDEX;
        /* must not change ad_spool[] */
        ad_type = p_ad->com.ad_type;
        sal_memcpy(&old_profile, pe->u.ad, size[ad_type]);
        CTC_ERROR_DUMP(ctc_spool_add(p_usw_scl_master[lchip]->ad_spool[scl_id*SYS_SCL_SW_AD_TYPE_IGS_MAX + ad_type], &new_profile, pe->u.ad, &out_profile));
        if (out_profile)
        {
            hw_ad_index = out_profile->com.ad_index;
            pe->u.ad = out_profile;
            spool_upddate = 1;
        }
    }

    /*write ad*/
    if (!pe->is_buffer)
    {
        uint32 cmd_ds = 0;

        DRV_IOCTL(lchip, hw_ad_index, DRV_CMD_BMP_EN(cmdw, MCHIP_FEATURE_PP_EN(lchip,CTC_FEATURE_SCL)), &action);
        if (SYS_SCL_IS_HASH_COM_MODE(pe))
        {
            cmd_ds = DRV_IOW(act_id1, DRV_ENTRY_FLAG);
            ret = ret ? ret: DRV_IOCTL(lchip, hw_ad_index, DRV_CMD_BMP_EN(cmd_ds, MCHIP_FEATURE_PP_EN(lchip,CTC_FEATURE_SCL)), &action);
        }
    }
    else
    {
        sal_memcpy(&pe->u.temp_entry->action, &action, sizeof(action));
    }

    /*update key for ad index not match*/
    if ((!pe->is_buffer) && (hw_ad_index != ((sys_scl_sw_igs_ad_t*)pe->u.ad)->com.ad_index) && igs_hash_key)
    {
        drv_acc_in_t in;
        drv_acc_out_t out;
        uint32 key_tbl[2] = {key_id, key_id1};
        void* p_ad = pe->u.ad;
        uint8 key_num = SYS_SCL_IS_HASH_COM_MODE(pe)?2:1;
        uint8 index = 0;
  
        sal_memset(&in, 0, sizeof(in));
        sal_memset(&out, 0, sizeof(out));
        sal_memset(&temp_entry, 0, sizeof(sys_scl_sw_temp_entry_t));

        for (index = 0; index < key_num; index++)
        {
            in.type = DRV_ACC_TYPE_LOOKUP;
            in.op_type = DRV_ACC_OP_BY_INDEX;
            in.tbl_id = key_tbl[index];
            in.data   = (void*)temp_entry.key;
            in.index  = hw_key_index;
            drv_acc_get_hash_module(lchip, in.tbl_id, &in.module);
            in.oper_bmp = DRV_ACC_BMP_EN(MCHIP_FEATURE_PP_EN(lchip, CTC_FEATURE_SCL));
            CTC_ERROR_GOTO(drv_acc_api(lchip, &in, &out), ret, error0);
  
            sal_memcpy(&temp_entry.key, out.data, sizeof(uint32) * SYS_SCL_MAX_KEY_SIZE_IN_WORD);

            temp_entry.p_ad = pe->u.ad;
            pe->u.temp_entry = &temp_entry;
            field_key.type = SYS_SCL_FIELD_KEY_AD_INDEX;
            field_key.data = hw_ad_index;
            CTC_ERROR_GOTO(p_usw_scl_master[lchip]->build_key_func[pe->key_type](lchip, &field_key, pe, TRUE), ret, error0);
  
            in.type = DRV_ACC_TYPE_ADD;
            in.op_type = DRV_ACC_OP_BY_INDEX;
            in.tbl_id = key_tbl[index];
            in.data   = (void*)&temp_entry.key;
            in.index  = hw_key_index;
            drv_acc_get_hash_module(lchip, in.tbl_id, &in.module);
            in.oper_bmp = DRV_ACC_BMP_EN(MCHIP_FEATURE_PP_EN(lchip, CTC_FEATURE_SCL));
            ret = drv_acc_api(lchip, &in, &out);
            if (ret)
            {
                SYS_SCL_DBG_OUT(CTC_DEBUG_LEVEL_ERROR, " Scl update ad process, write key failed, cannot rollback! \n");
            }
        }
        pe->u.temp_entry = NULL;
        pe->u.ad = p_ad;
    }
    if (p_dsnh_info->need_lock)
    {
        SYS_SCL_UNLOCK(lchip);
    }
    return CTC_E_NONE;

error0:
    if (spool_upddate == 1)
    {
        CTC_ERROR_DUMP(ctc_spool_add(p_usw_scl_master[lchip]->ad_spool[scl_id*SYS_SCL_SW_AD_TYPE_IGS_MAX + ad_type], &old_profile, pe->u.ad, &out_profile));
        pe->u.ad = out_profile;
    }
    if (p_dsnh_info->need_lock)
    {
        SYS_SCL_UNLOCK(lchip);
    }
    return ret;
}
#if 0
STATIC void
_sys_tmm_scl_rebuild_temp_ds(uint8 lchip, void* ds)
{
    uint8  data_valid = 0;
    uint32 zero[2] = {0};
    uint32 tmp_data[2] = {0};

    GetDsUserId(A, u1_data_f, ds, tmp_data);
    data_valid = (0 != sal_memcmp(tmp_data, zero, sizeof(zero)));
    switch(GetDsUserId(V, u1Type_f, ds))
    {
        case 0:
            if (data_valid != 0)
            {
                sal_memcpy(SYS_SCL_TEMP_USERID(ds, SYS_SCL_USERID_BMP_U1_G1), tmp_data, sizeof(tmp_data));
            }
            break;
        case 1:
            if (data_valid != 0)
            {
                sal_memcpy(SYS_SCL_TEMP_USERID(ds, SYS_SCL_USERID_BMP_FLOW), tmp_data, sizeof(tmp_data));
            }
            break;
        case 2:
            if (data_valid != 0)
            {
                sal_memcpy(SYS_SCL_TEMP_USERID(ds, SYS_SCL_USERID_BMP_VLAN_XLATE), tmp_data, sizeof(tmp_data));
            }
            break;
        case 3:
            if (data_valid != 0)
            {
                sal_memcpy(SYS_SCL_TEMP_USERID(ds, SYS_SCL_USERID_BMP_FWD), tmp_data, sizeof(tmp_data));
            }
            break;
        default:
            break;
    }
    sal_memset(tmp_data, 0, sizeof(tmp_data));
    switch(GetDsUserId(V, uType_f, ds))
    {
        case 0:
            GetDsUserId(A, u_g1_logicPort_f, ds, tmp_data);
            if (0 != sal_memcmp(tmp_data, zero, sizeof(zero)))
            {
                sal_memcpy(SYS_SCL_TEMP_USERID(ds, SYS_SCL_USERID_BMP_LOGIC_PORT), tmp_data, sizeof(tmp_data));
            }
            sal_memset(tmp_data, 0, sizeof(tmp_data));
            GetDsUserId(A, u_g1_vlanXlate_f, ds, tmp_data);
            if (0 != sal_memcmp(tmp_data, zero, sizeof(zero)))
            {
                sal_memcpy(SYS_SCL_TEMP_USERID(ds, SYS_SCL_USERID_BMP_VLAN_XLATE), tmp_data, sizeof(tmp_data));
            }
            break;
        case 1:
            GetDsUserId(A, u_g2_fwd_f, ds, tmp_data);
            if (0 != sal_memcmp(tmp_data, zero, sizeof(zero)))
            {
                sal_memcpy(SYS_SCL_TEMP_USERID(ds, SYS_SCL_USERID_BMP_FWD), tmp_data, sizeof(tmp_data));
            }
            sal_memset(tmp_data, 0, sizeof(tmp_data));
            GetDsUserId(A, u_g2_vlanXlate_f, ds, tmp_data);
            if (0 != sal_memcmp(tmp_data, zero, sizeof(zero)))
            {
                sal_memcpy(SYS_SCL_TEMP_USERID(ds, SYS_SCL_USERID_BMP_VLAN_XLATE), tmp_data, sizeof(tmp_data));
            }
            break;
        case 2:
            GetDsUserId(A, u_g3_binding_f, ds, tmp_data);
            if (0 != sal_memcmp(tmp_data, zero, sizeof(zero)))
            {
                sal_memcpy(SYS_SCL_TEMP_USERID(ds, SYS_SCL_USERID_BMP_BINDING), tmp_data, sizeof(tmp_data));
            }
            sal_memset(tmp_data, 0, sizeof(tmp_data));
            GetDsUserId(A, u_g3_fwd_f, ds, tmp_data);
            if (0 != sal_memcmp(tmp_data, zero, sizeof(zero)))
            {
                sal_memcpy(SYS_SCL_TEMP_USERID(ds, SYS_SCL_USERID_BMP_FWD), tmp_data, sizeof(tmp_data));
            }
            break;
        case 3:
            GetDsUserId(A, u_g4_flow_f, ds, tmp_data);
            if (0 != sal_memcmp(tmp_data, zero, sizeof(zero)))
            {
                sal_memcpy(SYS_SCL_TEMP_USERID(ds, SYS_SCL_USERID_BMP_FLOW), tmp_data, sizeof(tmp_data));
            }
            sal_memset(tmp_data, 0, sizeof(tmp_data));
            GetDsUserId(A, u_g4_portExtender_f, ds, tmp_data);
            if (0 != sal_memcmp(tmp_data, zero, sizeof(zero)))
            {
                sal_memcpy(SYS_SCL_TEMP_USERID(ds, SYS_SCL_USERID_BMP_PORT_EXTENDER), tmp_data, sizeof(tmp_data));
            }
            break;
        case 4:
            GetDsUserId(A, u_g5_flow_f, ds, tmp_data);
            if (0 != sal_memcmp(tmp_data, zero, sizeof(zero)))
            {
                sal_memcpy(SYS_SCL_TEMP_USERID(ds, SYS_SCL_USERID_BMP_FLOW), tmp_data, sizeof(tmp_data));
            }
            sal_memset(tmp_data, 0, sizeof(tmp_data));
            GetDsUserId(A, u_g5_fwd_f, ds, tmp_data);
            if (0 != sal_memcmp(tmp_data, zero, sizeof(zero)))
            {
                sal_memcpy(SYS_SCL_TEMP_USERID(ds, SYS_SCL_USERID_BMP_FWD), tmp_data, sizeof(tmp_data));
            }
            break;
        case 5:
            GetDsUserId(A, u_g6_fwd_f, ds, tmp_data);
            if (0 != sal_memcmp(tmp_data, zero, sizeof(zero)))
            {
                sal_memcpy(SYS_SCL_TEMP_USERID(ds, SYS_SCL_USERID_BMP_FWD), tmp_data, sizeof(tmp_data));
            }
            sal_memset(tmp_data, 0, sizeof(tmp_data));
            GetDsUserId(A, u_g6_logicPort_f, ds, tmp_data);
            if (0 != sal_memcmp(tmp_data, zero, sizeof(zero)))
            {
                sal_memcpy(SYS_SCL_TEMP_USERID(ds, SYS_SCL_USERID_BMP_LOGIC_PORT), tmp_data, sizeof(tmp_data));
            }
            break;
        case 6:
            GetDsUserId(A, u_g7_flow_f, ds, tmp_data);
            if (0 != sal_memcmp(tmp_data, zero, sizeof(zero)))
            {
                sal_memcpy(SYS_SCL_TEMP_USERID(ds, SYS_SCL_USERID_BMP_FLOW), tmp_data, sizeof(tmp_data));
            }
            sal_memset(tmp_data, 0, sizeof(tmp_data));
            GetDsUserId(A, u_g7_logicPort_f, ds, tmp_data);
            if (0 != sal_memcmp(tmp_data, zero, sizeof(zero)))
            {
                sal_memcpy(SYS_SCL_TEMP_USERID(ds, SYS_SCL_USERID_BMP_LOGIC_PORT), tmp_data, sizeof(tmp_data));
            }
            break;
        case 7:
            GetDsUserId(A, u_g8_flow_f, ds, tmp_data);
            if (0 != sal_memcmp(tmp_data, zero, sizeof(zero)))
            {
                sal_memcpy(SYS_SCL_TEMP_USERID(ds, SYS_SCL_USERID_BMP_FLOW), tmp_data, sizeof(tmp_data));
            }
            sal_memset(tmp_data, 0, sizeof(tmp_data));
            GetDsUserId(A, u_g8_vlanXlate_f, ds, tmp_data);
            if (0 != sal_memcmp(tmp_data, zero, sizeof(zero)))
            {
                sal_memcpy(SYS_SCL_TEMP_USERID(ds, SYS_SCL_USERID_BMP_VLAN_XLATE), tmp_data, sizeof(tmp_data));
            }
            break;
        default:
            break;
    }
}
#endif
int32
sys_tmm_scl_get_userid_default_action(uint8 lchip, sys_scl_default_action_t* p_default_action)
{
#ifdef __TODO__
    uint8 step = 0;
    uint8 fpa_size = 0;
    uint16 lport = p_default_action->lport % MCHIP_CAP(SYS_CAP_PER_SLICE_PORT_NUM);
    uint32 tbl_id = 0;
    uint32 cmd = 0;
    ds_t ds_userid;
    void *temp_flow = NULL, *temp_fwd = NULL, *temp_logic_port = NULL, *temp_vlan_xlate = NULL;
    sys_scl_sw_entry_t *pe = NULL;
    sys_scl_flexed_key_t* p_flexed_key = NULL;
    if (p_default_action->action_type != SYS_SCL_ACTION_INGRESS)
    {
        return CTC_E_NONE;
    }
    sal_memset(&ds_userid, 0, sizeof(ds_t));
    if (p_default_action->is_vlan_class)
    {
        _sys_usw_scl_get_nodes_by_eid(lchip, p_default_action->eid, &pe);

        if (NULL == pe)
        {
            SYS_SCL_DBG_OUT(CTC_DEBUG_LEVEL_ERROR, " Entry not found \n");
            return CTC_E_NOT_EXIST;
        }
        p_flexed_key = (sys_scl_flexed_key_t*)(pe->fk);
        SYS_SCL_ENCODE_XKEY_FPA_SIZE(p_flexed_key, pe, fpa_size)
        /* for tacm entry, key index is equal to ad_index in the scale of 80 bit regardless of key type,
        so in our per entry sw table, the key index and ad_index is 80bit not in the form of hw table */
        p_default_action->ad_index[0] = pe->key_index;
        step = SYS_SCL_GET_STEP(fpa_size);
        p_default_action->ad_index[0] = SYS_SCL_MAP_DRV_AD_INDEX(p_default_action->ad_index[0], step);

        if (NULL == pe->group)
        {
            SYS_SCL_DBG_OUT(CTC_DEBUG_LEVEL_ERROR, " Entry not found \n");
            return CTC_E_NOT_EXIST;
        }
        else
        {
            switch(pe->group->priority)
            {
                case 0 :
                    tbl_id = DsUserId0Tcam_t;
                    break;
                case 1 :
                    tbl_id = DsUserId1Tcam_t;
                    break;
                case 2 :
                    tbl_id = DsUserId2_t;
                    break;
                case 3 :
                    tbl_id = DsUserId3_t;
                    break;
                default :
                    SYS_SCL_DBG_OUT(CTC_DEBUG_LEVEL_ERROR, " Invalid scl id \n");
                    return CTC_E_INTR_INVALID_PARAM;
            }
        }
    }
    else
    {
        if (lport  >= SYS_USW_MAX_PORT_NUM_PER_CHIP)
        {
            SYS_SCL_DBG_OUT(CTC_DEBUG_LEVEL_ERROR, " [SCL] Invalid default port\n");
            return CTC_E_INVALID_PORT;

        }
        p_default_action->ad_index[p_default_action->scl_id] = p_usw_scl_master[lchip]->igs_default_base[p_default_action->scl_id] + 2 * lport;

        tbl_id = (p_default_action->scl_id == 0? DsUserId_t : DsUserId1_t);
    }
    cmd = DRV_IOR(tbl_id, DRV_ENTRY_FLAG);
    CTC_ERROR_RETURN(DRV_IOCTL(lchip, p_default_action->ad_index[p_default_action->scl_id] , DRV_CMD_BMP_EN(cmd, MCHIP_FEATURE_PP_EN(lchip,CTC_FEATURE_SCL)), &ds_userid));

    _sys_tmm_scl_rebuild_temp_ds(lchip, &ds_userid);

    /* the sequence can not be changed */
    temp_flow = SYS_SCL_TEMP_USERID(&ds_userid, SYS_SCL_USERID_BMP_FLOW);
    temp_fwd = SYS_SCL_TEMP_USERID(&ds_userid, SYS_SCL_USERID_BMP_FWD);
    temp_logic_port = SYS_SCL_TEMP_USERID(&ds_userid, SYS_SCL_USERID_BMP_LOGIC_PORT);
    temp_vlan_xlate = SYS_SCL_TEMP_USERID(&ds_userid, SYS_SCL_USERID_BMP_VLAN_XLATE);
    if (GetTempDsFlow(V, exceptionEn_f, temp_flow))
    {/*To CPU*/
        p_default_action->vlan_miss->flag = CTC_VLAN_MISS_ACTION_TO_CPU;
    }
    else if ( GetDsUserId(V, bypassAll_f, &ds_userid)
            && GetTempDsFwdInfo(V, u2Type_f, temp_fwd) == 0
            && GetTempDsFwdInfo(V, u2_g1_dsFwdPtr_f, temp_fwd) == 0xFFFF)
    { /*drop*/
        p_default_action->vlan_miss->flag = CTC_VLAN_MISS_ACTION_DISCARD;
    }
    else if (GetTempDsLogicPort(V, vsiIdValid_f, temp_logic_port) == 0 &&
             GetTempDsLogicPort(V, vsiIdOrUserVlanPtr_f, temp_logic_port) != 0)
    {/*user vlanptr*/
        p_default_action->vlan_miss->user_vlanptr = GetTempDsLogicPort(V, vsiIdOrUserVlanPtr_f, temp_logic_port);
        p_default_action->vlan_miss->flag = CTC_VLAN_MISS_ACTION_OUTPUT_VLANPTR;
    }

    else if (GetTempDsVlanXlate(V, vlanActionProfileValid_f, temp_vlan_xlate))

    {/*vlan id*/
        p_default_action->vlan_miss->new_svid = GetTempDsVlanXlate(V, userSvlanId_f, temp_vlan_xlate);
        p_default_action->vlan_miss->new_scos =  GetTempDsVlanXlate(V, userScos_f, temp_vlan_xlate);
        p_default_action->vlan_miss->flag = CTC_VLAN_MISS_ACTION_APPEND_STAG;
    }
    else
    {
       p_default_action->vlan_miss->flag = CTC_VLAN_MISS_ACTION_DO_NOTHING;
    }
#endif
    return CTC_E_NONE;
}
/*
int32
_sys_tmm_map_aset_to_userid_bmp(uint8 lchip, uint32* action_bmp, uint8* bmp, uint8* u3_type,uint8* u2_type,uint32* chunk_bmp)
{
    uint8 loop = 0;
    uint8 userid_bitmap = *bmp;
    for(; loop < CTC_SCL_FIELD_ACTION_TYPE_NUM; loop++)
    {
        if(!CTC_BMP_ISSET(action_bmp, loop))
        {
            continue;
        }
        switch(loop)
        {
        case CTC_SCL_FIELD_ACTION_TYPE_FLOW_LKUP_BY_OUTER_HEAD:
        case CTC_SCL_FIELD_ACTION_TYPE_IPFIX_LKUP_BY_OUTER_HEAD:
        case CTC_SCL_FIELD_ACTION_TYPE_FORCE_BRIDGE:
        case CTC_SCL_FIELD_ACTION_TYPE_FORCE_LEARNING:
        case CTC_SCL_FIELD_ACTION_TYPE_FORCE_ROUTE:
            if(CTC_BMP_ISSET(action_bmp, CTC_SCL_FIELD_ACTION_TYPE_POLICER_ID) || CTC_BMP_ISSET(action_bmp, CTC_SCL_FIELD_ACTION_TYPE_COS_HBWP_POLICER))
            {
                CTC_BIT_SET(userid_bitmap, SYS_SCL_USERID_BMP_U1_G1);
            }
            else
            {
                *u3_type = SYS_AD_UNION_G_2;
            }
            break;
        case CTC_SCL_FIELD_ACTION_TYPE_SERVICE_ACL_EN:
        case CTC_SCL_FIELD_ACTION_TYPE_MAC_LIMIT_DISCARD_EN:
        case CTC_SCL_FIELD_ACTION_TYPE_ACL_TCAM_EN:
        case CTC_SCL_FIELD_ACTION_TYPE_ACL_HASH_EN:
            return CTC_E_NOT_SUPPORT;
        
        case CTC_SCL_FIELD_ACTION_TYPE_LOGIC_PORT:
        case CTC_SCL_FIELD_ACTION_TYPE_LOGIC_PORT_SECURITY_EN:
        case CTC_SCL_FIELD_ACTION_TYPE_MAC_LIMIT:
        case CTC_SCL_FIELD_ACTION_TYPE_USER_VLANPTR:
        case SYS_SCL_FIELD_ACTION_TYPE_PON_SERVICE:
        case CTC_SCL_FIELD_ACTION_TYPE_QOS_MAP:
            CTC_BIT_SET(userid_bitmap, SYS_SCL_USERID_BMP_LOGIC_PORT);
            break;
        case CTC_SCL_FIELD_ACTION_TYPE_METADATA:
            if(DRV_IS_TMM(lchip) || (*u2_type != SYS_AD_UNION_G_NA))
            {
                CTC_BIT_SET(userid_bitmap, SYS_SCL_USERID_BMP_U1_G1);
            }
            break;
        case CTC_SCL_FIELD_ACTION_TYPE_XDATA:
            if(CTC_FLAG_ISSET(*chunk_bmp,SYS_SCL_XDATA_IGS_CHUNK1_NIBBLE3_0))
            {
               CTC_BIT_SET(userid_bitmap, SYS_SCL_USERID_BMP_U1_G1);
            }
            break;
        case CTC_SCL_FIELD_ACTION_TYPE_IGMP_SNOOP_EN:
        case CTC_SCL_FIELD_ACTION_TYPE_STP_ID:
        case CTC_SCL_FIELD_ACTION_TYPE_ARP:
        case CTC_SCL_FIELD_ACTION_TYPE_IPV4_BASED_L2MC:
        case CTC_SCL_FIELD_ACTION_TYPE_IPV6_BASED_L2MC:
        //case CTC_SCL_FIELD_ACTION_TYPE_OAM_TUNNEL_EN:
            CTC_BIT_SET(userid_bitmap, SYS_SCL_USERID_BMP_U1_G1);
            break;
        case CTC_SCL_FIELD_ACTION_TYPE_APS:
        case CTC_SCL_FIELD_ACTION_TYPE_REDIRECT_PORT:
        case CTC_SCL_FIELD_ACTION_TYPE_REDIRECT:
            CTC_BIT_SET(userid_bitmap, SYS_SCL_USERID_BMP_FWD);
            CTC_BIT_SET(userid_bitmap, SYS_SCL_USERID_BMP_LOGIC_PORT);
            break;
        case CTC_SCL_FIELD_ACTION_TYPE_FID:
        case CTC_SCL_FIELD_ACTION_TYPE_VRFID:
            CTC_BIT_SET(userid_bitmap, SYS_SCL_USERID_BMP_FWD);
            break;
        case CTC_SCL_FIELD_ACTION_TYPE_HMAC_ID:
            CTC_BIT_SET(userid_bitmap, SYS_SCL_USERID_BMP_U1_G1);
            CTC_BIT_SET(userid_bitmap, SYS_SCL_USERID_BMP_FWD);
            break;
        case CTC_SCL_FIELD_ACTION_TYPE_COPY_TO_CPU:
        case CTC_SCL_FIELD_ACTION_TYPE_LB_HASH_SELECT_ID:
        case CTC_SCL_FIELD_ACTION_TYPE_FORCE_DECAP:
        case CTC_SCL_FIELD_ACTION_TYPE_SNOOPING_PARSER:
        case CTC_SCL_FIELD_ACTION_TYPE_FLEX_EDIT:
            CTC_BIT_SET(userid_bitmap, SYS_SCL_USERID_BMP_FLOW);
            break;
        case CTC_SCL_FIELD_ACTION_TYPE_VLAN_EDIT:
            CTC_BIT_SET(userid_bitmap, SYS_SCL_USERID_BMP_VLAN_XLATE);
            break;
        case CTC_SCL_FIELD_ACTION_TYPE_BINDING_EN:
            CTC_BIT_SET(userid_bitmap, SYS_SCL_USERID_BMP_BINDING);
            break;
        case CTC_SCL_FIELD_ACTION_TYPE_OAM:
            CTC_BIT_SET(userid_bitmap, SYS_SCL_USERID_BMP_LOGIC_PORT);
            break;
        case CTC_SCL_FIELD_ACTION_TYPE_ROUTER_MAC_MATCH:
            CTC_BIT_SET(userid_bitmap, SYS_SCL_USERID_BMP_PORT_EXTENDER);
            break;
        default:
            break;
        }
    }
    if ((userid_bitmap<=0x17 && userid_bitmap>=0x13) || (userid_bitmap<=0x1F && userid_bitmap>=0x1B) || \
       (userid_bitmap<=0x27 && userid_bitmap>=0x24) || (userid_bitmap<=0x3F && userid_bitmap>=0x2A) || \
       (userid_bitmap<=0x4F && userid_bitmap>=0x4D) || (userid_bitmap<=0x57 && userid_bitmap>=0x51) || \
       (userid_bitmap<=0x5F && userid_bitmap>=0x59) || (userid_bitmap<=0x7F && userid_bitmap>=0x62) || \
       (userid_bitmap==0x0F) || (userid_bitmap==0x47) || (userid_bitmap==0x4B) ))
       
    {
        SYS_SCL_DBG_OUT(CTC_DEBUG_LEVEL_ERROR, " %% SCL # userid_bitmap: 0x%X\n", userid_bitmap);
        CTC_ERROR_RETURN(CTC_E_NOT_SUPPORT);
    }
    *bmp = userid_bitmap;
    return CTC_E_NONE;
}
*/
int32
_sys_tmm_scl_check_fwd_type(uint8 lchip, uint32* action_bmp,uint8* fwd_u_type, uint8* fwd_u2_type, uint8 * pfwd_bmp)
{
    uint8 ug1_flag = 0, ug3_flag = 0, ug4_flag = 0, u2g1_flag = *fwd_u2_type, u2g2_flag = 0;
    uint8 fwd_bmp = 0;
    if(CTC_BMP_ISSET(action_bmp, CTC_SCL_FIELD_ACTION_TYPE_REDIRECT) ||
       CTC_BMP_ISSET(action_bmp, CTC_SCL_FIELD_ACTION_TYPE_REDIRECT_PORT)||
       CTC_BMP_ISSET(action_bmp, CTC_SCL_FIELD_ACTION_TYPE_DISCARD))
    {
        CTC_BIT_SET(fwd_bmp, 2);
    }

    if(CTC_BMP_ISSET(action_bmp,  CTC_SCL_FIELD_ACTION_TYPE_FID))
    {
        CTC_BIT_SET(fwd_bmp, 1);
        ug4_flag =SYS_AD_UNION_G_4;
    }
    if(CTC_BMP_ISSET(action_bmp,  CTC_SCL_FIELD_ACTION_TYPE_VRFID))
    {
        CTC_BIT_SET(fwd_bmp, 0);
        if(CTC_IS_BIT_SET(fwd_bmp, 1))
        {
            u2g1_flag = SYS_AD_UNION_G_1;
        }
        else
        {
            ug4_flag = SYS_AD_UNION_G_4;
        }
    }
    if (fwd_bmp==7)
    {
        SYS_SCL_DBG_OUT(CTC_DEBUG_LEVEL_ERROR, "  Redirect/discard, fid and vrfid can't be used together! Line: %u \n", __LINE__);
        return CTC_E_PARAM_CONFLICT;
    }

    ug1_flag = CTC_BMP_ISSET(action_bmp, CTC_SCL_FIELD_ACTION_TYPE_APS)?SYS_AD_UNION_G_1 : ug1_flag;
    if(CTC_BMP_ISSET(action_bmp, CTC_SCL_FIELD_ACTION_TYPE_HMAC_ID))
    {
        ug3_flag = SYS_AD_UNION_G_3;
        u2g2_flag = SYS_AD_UNION_G_2;
    }
    if(!ug1_flag + !ug3_flag + !ug4_flag >= 2 && !u2g1_flag + !u2g2_flag >= 1)
    {
        *fwd_u_type = ug1_flag + ug3_flag + ug4_flag;
        *fwd_u2_type = u2g1_flag + u2g2_flag;
    }
    else
    {
        return CTC_E_PARAM_CONFLICT;
    }

    if(CTC_BMP_ISSET(action_bmp, CTC_SCL_FIELD_ACTION_TYPE_REDIRECT) || CTC_BMP_ISSET(action_bmp, CTC_SCL_FIELD_ACTION_TYPE_REDIRECT_PORT))
    {
        if(ug1_flag || ug3_flag ||ug4_flag )
        {
            return CTC_E_PARAM_CONFLICT;
        }
    }
    *pfwd_bmp = fwd_bmp;
    return CTC_E_NONE;
}

#if 0

int32
sys_tmm_scl_check_aset(uint8 lchip, uint32* action_bmp, void* pe_info)
{
    int32 ret = CTC_E_NONE;


    uint32 chunk_bmp = 0;
    
    sys_scl_sw_entry_t* pe = (sys_scl_sw_entry_t*)pe_info;
    uint8 u2_type = 0, u3_type = 0;
    uint8 fwd_u_type = 0, fwd_u2_type = 0;
    uint8 u3g1_flag = 0, u3g2_flag = 0;
    uint8 u2g1_flag = 0, u2g2_flag=0, u2g4_flag = 0;
    uint8 userid_bmp = 0;
    uint8 fwd_bmp ;

    if(CTC_BMP_ISSET(action_bmp, CTC_SCL_FIELD_ACTION_TYPE_XDATA) && ((ret = _sys_usw_scl_check_xdata(lchip,pe,pe->action_bmp,&chunk_bmp))!= CTC_E_NONE))
    {
        return ret;
    }
    
    if ((CTC_BMP_ISSET(action_bmp, CTC_SCL_FIELD_ACTION_TYPE_FID) && CTC_BMP_ISSET(action_bmp, CTC_SCL_FIELD_ACTION_TYPE_VNI)) || 
        (CTC_BMP_ISSET(action_bmp, CTC_SCL_FIELD_ACTION_TYPE_FLEX_EDIT) && (CTC_BMP_ISSET(action_bmp, SYS_SCL_FIELD_ACTION_TYPE_SRV6) || 
                                                                      CTC_BMP_ISSET(action_bmp, CTC_SCL_FIELD_ACTION_TYPE_LB_HASH_SELECT_ID))) ||
        (CTC_BMP_ISSET(action_bmp, CTC_SCL_FIELD_ACTION_TYPE_FLEX_EDIT) && CTC_BMP_ISSET(action_bmp, CTC_SCL_FIELD_ACTION_TYPE_L3IF_PROPERTY)) ||
        (CTC_BMP_ISSET(action_bmp, CTC_SCL_FIELD_ACTION_TYPE_ISOLATION_ID) && CTC_BMP_ISSET(action_bmp, CTC_SCL_FIELD_ACTION_TYPE_RANDOM_LOG)) ||
        (CTC_BMP_ISSET(action_bmp, SYS_SCL_FIELD_ACTION_TYPE_SRV6) && CTC_BMP_ISSET(action_bmp, CTC_SCL_FIELD_ACTION_TYPE_L3IF_PROPERTY)) ||
        (CTC_FLAG_ISSET(chunk_bmp,SYS_SCL_XDATA_IGS_CHUNK1_NIBBLE3_0) && (CTC_BMP_ISSET(action_bmp, SYS_SCL_FIELD_ACTION_TYPE_SRV6) ||
                                                                        (CTC_BMP_ISSET(action_bmp,CTC_SCL_FIELD_ACTION_TYPE_METADATA) && 
                                                                        (CTC_BMP_ISSET(action_bmp,CTC_SCL_FIELD_ACTION_TYPE_SRC_CID)|| CTC_BMP_ISSET(action_bmp, CTC_SCL_FIELD_ACTION_TYPE_DST_CID)))))||                                                            
        ((CTC_FLAG_ISSET(chunk_bmp,SYS_SCL_XDATA_IGS_CHUNK1_NIBBLE3_0) && (CTC_FLAG_ISSET(chunk_bmp,SYS_SCL_XDATA_IGS_CHUNK2_BYTE0) || CTC_FLAG_ISSET(chunk_bmp,SYS_SCL_XDATA_IGS_CHUNK2_BYTE1)))&&
                                                                         (CTC_BMP_ISSET(action_bmp,CTC_SCL_FIELD_ACTION_TYPE_METADATA)||
                                                                         (CTC_BMP_ISSET(action_bmp,CTC_SCL_FIELD_ACTION_TYPE_SRC_CID)|| CTC_BMP_ISSET(action_bmp, CTC_SCL_FIELD_ACTION_TYPE_DST_CID))))||
        ((CTC_FLAG_ISSET(chunk_bmp,SYS_SCL_XDATA_IGS_CHUNK2_BYTE0) || CTC_FLAG_ISSET(chunk_bmp,SYS_SCL_XDATA_IGS_CHUNK2_BYTE1))&& (CTC_BMP_ISSET(action_bmp,CTC_SCL_FIELD_ACTION_TYPE_SRC_CID) ||
                                                                         CTC_BMP_ISSET(action_bmp, CTC_SCL_FIELD_ACTION_TYPE_DST_CID) ||
                                                                         CTC_BMP_ISSET(action_bmp,SYS_SCL_FIELD_ACTION_TYPE_SRV6)))||
        (CTC_FLAG_ISSET(chunk_bmp,SYS_SCL_XDATA_IGS_CHUNK3_WORD0) && (CTC_BMP_ISSET(action_bmp,CTC_SCL_FIELD_ACTION_TYPE_POLICER_ID) ||
                                                                         CTC_BMP_ISSET(action_bmp, CTC_SCL_FIELD_ACTION_TYPE_COS_HBWP_POLICER))))
    {
        return CTC_E_PARAM_CONFLICT;
    }
        
    if(CTC_FLAG_ISSET(chunk_bmp,SYS_SCL_XDATA_IGS_CHUNK3_WORD0) || CTC_BMP_ISSET(action_bmp, CTC_SCL_FIELD_ACTION_TYPE_POLICER_ID) ||
            CTC_BMP_ISSET(action_bmp, CTC_SCL_FIELD_ACTION_TYPE_COS_HBWP_POLICER))
    {
        u3g1_flag = SYS_AD_UNION_G_1;
    }
    if(CTC_BMP_ISSET(action_bmp,CTC_SCL_FIELD_ACTION_TYPE_EFD) || CTC_BMP_ISSET(action_bmp,CTC_SCL_FIELD_ACTION_TYPE_PTP_CLOCK_ID))

    {
        u3g2_flag = SYS_AD_UNION_G_2;
        if(u3g1_flag)
        {
            return CTC_E_PARAM_CONFLICT;
        }
    }
    
    if(CTC_BMP_ISSET(action_bmp,CTC_SCL_FIELD_ACTION_TYPE_SERVICE_ID) || CTC_BMP_ISSET(action_bmp,CTC_SCL_FIELD_ACTION_TYPE_UDF_ID))
    {
        u2g1_flag = SYS_AD_UNION_G_1;
    }
 
    if(CTC_BMP_ISSET(action_bmp,CTC_SCL_FIELD_ACTION_TYPE_SRC_CID) || CTC_BMP_ISSET(action_bmp,CTC_SCL_FIELD_ACTION_TYPE_DST_CID))
    {
        if((CTC_BMP_ISSET(action_bmp,CTC_SCL_FIELD_ACTION_TYPE_SRC_CID) && CTC_BMP_ISSET(action_bmp,CTC_SCL_FIELD_ACTION_TYPE_DST_CID))
            ||(CTC_BMP_ISSET(action_bmp,CTC_SCL_FIELD_ACTION_TYPE_METADATA ) && (DRV_IS_TMM(lchip) || DRV_IS_TMG(lchip))))

        {
            return CTC_E_PARAM_CONFLICT;
        }
        u2g2_flag = SYS_AD_UNION_G_2;
    }
    
    if(CTC_FLAG_ISSET(chunk_bmp,SYS_SCL_XDATA_IGS_CHUNK2_BYTE0) || CTC_FLAG_ISSET(chunk_bmp,SYS_SCL_XDATA_IGS_CHUNK2_BYTE1))
    {   
        u2g2_flag = SYS_AD_UNION_G_2;
    }
    if(CTC_BMP_ISSET(action_bmp,CTC_SCL_FIELD_ACTION_TYPE_SPAN_FLOW) || CTC_BMP_ISSET(action_bmp,CTC_SCL_FIELD_ACTION_TYPE_QOS_MAP) || CTC_BMP_ISSET(action_bmp,CTC_SCL_FIELD_ACTION_TYPE_LOCAL_ARP))
    {
        u2g4_flag = SYS_AD_UNION_G_4;
    }
    
    if(CTC_BMP_ISSET(action_bmp,CTC_SCL_FIELD_ACTION_TYPE_RANDOM_LOG))

    {
        if(!u3g1_flag)
        {
            u3g2_flag = SYS_AD_UNION_G_2;
        }
        else
        {
            u2g4_flag = SYS_AD_UNION_G_4;
        }
    }

    if(CTC_BMP_ISSET(action_bmp, CTC_SCL_FIELD_ACTION_TYPE_DISCARD))
    {
        CTC_BIT_SET(userid_bmp, (SYS_SCL_ACTION_FLOW == pe->action_type)? SYS_SCL_USERID_BMP_FLOW: SYS_SCL_USERID_BMP_FWD);
        fwd_u2_type = (SYS_SCL_ACTION_FLOW == pe->action_type) ? 0 : SYS_AD_UNION_G_1;
    }
    if(!u2g1_flag + !u2g2_flag + !u2g4_flag >= 2)
    {
        u2_type = u2g1_flag + u2g2_flag + u2g4_flag;
    }
    else
    {
        return CTC_E_PARAM_CONFLICT;
    }
    
    CTC_ERROR_RETURN(_sys_tmm_map_aset_to_userid_bmp(lchip, action_bmp, &userid_bmp, &u3g2_flag, &u2_type,&chunk_bmp));

	if(CTC_BMP_ISSET(action_bmp, CTC_SCL_FIELD_ACTION_TYPE_METADATA) && DRV_FROM_AT(lchip) && (u2_type == 0))
	{
        u2_type = SYS_AD_UNION_G_2;
	}

    if(!u3g1_flag + !u3g2_flag >= 1)
    {
        u3_type = u3g1_flag + u3g2_flag;
    }
    else
    {
        return CTC_E_PARAM_CONFLICT;
    }
    CTC_ERROR_RETURN(_sys_tmm_scl_check_fwd_type(action_bmp, &fwd_u_type, &fwd_u2_type, &fwd_bmp));
    pe->u.temp_entry->temp_ad.com.u2_type = u2_type;
    pe->u.temp_entry->temp_ad.com.u3_type = u3_type;
    pe->u.temp_entry->temp_ad.com.u4_type = fwd_u_type;
    pe->u.temp_entry->temp_ad.com.userid_bmp = userid_bmp;
    pe->u.temp_entry->temp_ad.com.fwd_bmp = fwd_bmp;
    pe->u.temp_entry->temp_ad.com.u1_type = CTC_IS_BIT_SET(userid_bmp,SYS_SCL_USERID_BMP_U1_G1) ? SYS_AD_UNION_G_1 : 0;

    return ret;
}
#endif

int32
sys_tmm_scl_add_compress_ether_type(uint8 lchip, uint16 new_ether_type, uint16 old_ether_type,uint8* o_cether_type, uint8* o_cether_type_index)
{
    uint32 cmd = 0;
    UserIdEtherTypeCompressCam_m    cam_cethertype;
    sys_register_cethertype_t new_cethertype_t = {0};
    sys_register_cethertype_t old_cethertype_t = {0};
    sys_register_cethertype_t*    pcether_get  = NULL;

    new_cethertype_t.ether_type = new_ether_type;
    new_cethertype_t.index.index = *o_cether_type_index;
    old_cethertype_t.ether_type = old_ether_type;
    SYS_SCL_INIT_CHECK();
    CTC_ERROR_RETURN(ctc_spool_add(p_usw_scl_master[lchip]->cethertype_spool,&new_cethertype_t,&old_cethertype_t, &pcether_get));
    if(o_cether_type)
    {
        sal_memset(&cam_cethertype, 0,sizeof(cam_cethertype));
        *o_cether_type = (1 << 6 | (pcether_get->index.index&0x3F));
        SetUserIdEtherTypeCompressCam(V, etherType_f, &cam_cethertype, pcether_get->ether_type);
        SetUserIdEtherTypeCompressCam(V, compressEtherType_f, &cam_cethertype, pcether_get->index.index);
        SetUserIdEtherTypeCompressCam(V, valid_f, &cam_cethertype, 1);
        cmd = DRV_IOW(UserIdEtherTypeCompressCam_t, DRV_ENTRY_FLAG);
        CTC_ERROR_RETURN(DRV_IOCTL(lchip, pcether_get->index.index, DRV_CMD_BMP_EN(cmd, MCHIP_FEATURE_PP_EN(lchip,CTC_FEATURE_SCL)), &cam_cethertype));
    }
    *o_cether_type_index = pcether_get->index.index & 0x3F;
    return CTC_E_NONE;
}

int32
sys_tmm_scl_remove_compress_ether_type(uint8 lchip, uint8 ether_type_index)
{
    uint16 ether_type = 0;
    uint32 cmd = 0;
    sys_register_cethertype_t cethertype_t = {0};
    UserIdEtherTypeCompressCam_m cam_cethertype;

    SYS_SCL_INIT_CHECK();

    sal_memset(&cam_cethertype, 0 , sizeof(UserIdEtherTypeCompressCam_m));

    cmd = DRV_IOR(UserIdEtherTypeCompressCam_t, DRV_ENTRY_FLAG);
    CTC_ERROR_RETURN(DRV_IOCTL(lchip, ether_type_index, DRV_CMD_PP_EN(cmd), &cam_cethertype));
    ether_type = GetUserIdEtherTypeCompressCam(V,etherType_f, &cam_cethertype);

    cethertype_t.ether_type = ether_type;
    CTC_ERROR_RETURN(ctc_spool_remove(p_usw_scl_master[lchip]->cethertype_spool, &cethertype_t, NULL));

    return CTC_E_NONE;
}

#if defined(ARCTIC)

int32
sys_at_entry_pp_hash_init(uint8 lchip)
{
    uint8 pp_num = SYS_PP_NUM(lchip);
    uint32 entry_num = 0;
    uint32 block_size = 0;
    
    if (SYS_VCHIP_PP_IS_NOT_BASE(lchip))
    {
        p_usw_scl_master[lchip]->entry_pp_hash = 
                p_usw_scl_master[drv_vchip_get_pp_base(lchip)]->entry_pp_hash;
        return CTC_E_NONE;
    }
  
    entry_num = SYS_SCL_ENTRY_HASH_SIZE*pp_num;
    block_size = CTC_HASH_1K_BLOCK_SIZE;
    p_usw_scl_master[lchip]->entry_pp_hash =  sys_usw_com_entry_hash_init(lchip, entry_num, block_size);
    
    if(!p_usw_scl_master[lchip]->entry_pp_hash)
    {
        return CTC_E_NO_MEMORY;
    }

    return CTC_E_NONE;
}


int32
sys_at_entry_pp_hash_deinit(uint8 lchip)
{
    if (SYS_VCHIP_PP_IS_NOT_BASE(lchip))
    {
        p_usw_scl_master[lchip]->entry_pp_hash = NULL;
        return CTC_E_NONE;
    }

    sys_usw_com_entry_hash_deinit(lchip,p_usw_scl_master[lchip]->entry_pp_hash);

    return CTC_E_NONE;
}

int32
sys_at_scl_build_hash_key_nsh(uint8 lchip, ctc_field_key_t* pKey, void* pe_info, uint8 is_add)
{
    void*      p_data = NULL;
    void*      p_mask = NULL;
    sys_scl_sw_entry_t* pe = (sys_scl_sw_entry_t*)pe_info;

    CTC_PTR_VALID_CHECK(pKey);
    CTC_PTR_VALID_CHECK(pe);
    CTC_PTR_VALID_CHECK(pe->u.temp_entry);

    p_data = (void*)pe->u.temp_entry->key;
    p_mask = (void*)pe->u.temp_entry->mask;

    switch (pKey->type)
    {
        case CTC_FIELD_KEY_NSH_SI:
            CTC_MAX_VALUE_CHECK(pKey->data, 0xFF);
            SetDsUserIdNshHashKey(V, nshSi_f, p_data, pKey->data);
            SetDsUserIdNshHashKey(V, nshSi_f, p_mask, pKey->data);
            CTC_BMP_UNSET(pe->u.temp_entry->hash_sel_bmp, DsUserIdNshHashKey_nshSi_f);
            break;

        case CTC_FIELD_KEY_NSH_SPI:
            CTC_MAX_VALUE_CHECK(pKey->data, 0xFFFFFF);
            SetDsUserIdNshHashKey(V, nshSpi_f, p_data, pKey->data);
            SetDsUserIdNshHashKey(V, nshSpi_f, p_mask, pKey->data);
            CTC_BMP_UNSET(pe->u.temp_entry->hash_sel_bmp, DsUserIdNshHashKey_nshSpi_f);
            break;

        case CTC_FIELD_KEY_HASH_VALID:
            SetDsUserIdNshHashKey(V, valid_f, p_data, 1);
            CTC_BMP_UNSET(pe->u.temp_entry->hash_sel_bmp, DsUserIdNshHashKey_valid_f);
            break;
        case SYS_SCL_FIELD_KEY_COMMON:
            SetDsUserIdNshHashKey(V, hashType_f, p_data, DRV_ENUM(DRV_USERIDHASHTYPE_NSH));
            SetDsUserIdNshHashKey(V, hashType_f, p_mask, 0xFF);
            CTC_BMP_UNSET(pe->u.temp_entry->hash_sel_bmp, DsUserIdNshHashKey_hashType_f);
            CTC_BMP_UNSET(pe->u.temp_entry->hash_sel_bmp, DsUserIdNshHashKey_dsAdIndex_f);
            CTC_BMP_UNSET(pe->u.temp_entry->hash_sel_bmp, DsUserIdNshHashKey_isLabel_f);
            CTC_BMP_UNSET(pe->u.temp_entry->hash_sel_bmp, DsUserIdNshHashKey_isLogicPort_f);
            CTC_BMP_UNSET(pe->u.temp_entry->hash_sel_bmp, DsUserIdNshHashKey_globalSrcPort_f);
            break;
        case SYS_SCL_FIELD_KEY_AD_INDEX:
            SetDsUserIdNshHashKey(V, dsAdIndex_f, p_data, pKey->data);
            break;
        default:
            SYS_SCL_DBG_OUT(CTC_DEBUG_LEVEL_ERROR, " API or some feature is not supported \n");
            return CTC_E_NOT_SUPPORT;
    }

    return CTC_E_NONE;
}

int32
_sys_at_scl_array_is_empty(uint8* array, uint32 len)
{
    uint32 loop = 0;
    do
    {
        if (array[loop++] != 0)
        {
            return FALSE;
        }
    }while(loop<len);
    return TRUE;
}

int32
_sys_at_scl_map_fk_field_type(uint8 lchip, uint16 field_type, uint8* p_fk_field_type, ctc_scl_flex_key_t* scl_flex_key, uint8* num)
{
    uint8 field_num = 0;
    uint8 i;
    uint32 fk_udf[] = {SYS_FK_F_UDF_DATA0,SYS_FK_F_UDF_DATA1,
                         SYS_FK_F_UDF_DATA2,SYS_FK_F_UDF_DATA3,
                         SYS_FK_F_UDF_DATA4,SYS_FK_F_UDF_DATA5,
                         SYS_FK_F_UDF_DATA6,SYS_FK_F_UDF_DATA7};
    switch(field_type)
    {
        case SYS_SCL_FIELD_KEY_EXT_TYPE:
            *p_fk_field_type = SYS_FK_F_PR_EXT_TYPE;
            field_num = 1;
            break;
        case CTC_FIELD_KEY_L4_TYPE:
            *p_fk_field_type = SYS_FK_F_PR_L4_TYPE;
            field_num = 1;
            break;
        case CTC_FIELD_KEY_L4_USER_TYPE:
            *p_fk_field_type = SYS_FK_F_PR_L4_USER_TYPE;
            field_num = 1;
            break;
        case CTC_FIELD_KEY_SVLAN_RANGE:
        case CTC_FIELD_KEY_CVLAN_RANGE:
            *p_fk_field_type = SYS_FK_F_VLAN_RANGE_MAX_LO;
            *(p_fk_field_type + 1) = SYS_FK_F_VLAN_RANGE_MAX_HI;
            *(p_fk_field_type + 2) = SYS_FK_F_VLAN_RANGE_VALID;
            *(p_fk_field_type + 3) = SYS_FK_F_VLAN_RANGE_TYPE;
            field_num = 4;
            break;
        case CTC_FIELD_KEY_UDF:
            for (i = 0; i < CTC_ACL_UDF_FIELD_NUM; i++)
            {
                if (!CTC_IS_BIT_SET(scl_flex_key->udf_bmp, i))
                {
                    continue;
                }
                *(p_fk_field_type + field_num) = fk_udf[i];
                field_num++;
            }
            *(p_fk_field_type + field_num) = SYS_FK_F_UDF_HIT_INDEX_LO;
            field_num++;
            break;
        case CTC_FIELD_KEY_PKT_FWD_TYPE:
            *p_fk_field_type = SYS_FK_F_PKT_FWD_TYPE;
            field_num = 1;
            break;
        case CTC_FIELD_KEY_DST_CID:
            *p_fk_field_type = SYS_FK_F_DST_CID;
            field_num = 1;
            break;
        case CTC_FIELD_KEY_IP_HDR_ERROR:
            *p_fk_field_type = SYS_FK_F_PR_IP_HDR_ERROR;
            field_num = 1;
            break;
        case CTC_FIELD_KEY_L2_TYPE:
            *p_fk_field_type = SYS_FK_F_PR_L2_TYPE;
            field_num = 1;
            break;
        case CTC_FIELD_KEY_L3_TYPE:
            *p_fk_field_type = SYS_FK_F_PR_L3_TYPE;
            field_num = 1;
            break;
        case CTC_FIELD_KEY_VLAN_NUM:
            *p_fk_field_type = SYS_FK_F_PR_VLAN_NUM;
            field_num = 1;
            break;
        case CTC_FIELD_KEY_IP_FRAG:
            *p_fk_field_type = SYS_FK_F_PR_FRAG_INFO;
            field_num = 1;
            break;
        case CTC_FIELD_KEY_XDATA:
            for(i = 0; i<scl_flex_key->xdata->num;i++)
            {
                *(p_fk_field_type+i) = SYS_FK_F_XDATA;
            }
            field_num = scl_flex_key->xdata->num;
            break;

        default:
            return CTC_E_INVALID_PARAM;
    }
    if (num)
    {
        *num = field_num;
    }
    return CTC_E_NONE;
}


int32
sys_at_scl_set_xkey_valid(uint8 lchip, void* user_data, uint8 is_add)
{
    sys_scl_sw_entry_t* pe = (sys_scl_sw_entry_t*) user_data;
    sys_scl_flexed_key_t* p_flexed_key = NULL;
    uint8 is_tcam = 0;
    uint8 drv_key_type = 0;

    CTC_PTR_VALID_CHECK(pe);
    p_flexed_key = (sys_scl_flexed_key_t*)(pe->u.temp_entry->fk);
    if (!p_flexed_key || !p_flexed_key->is_xkey)
    {
        return CTC_E_NONE;
    }
    is_tcam = SCL_ENTRY_IS_TCAM(p_flexed_key->origin_key_type);
    if (CTC_INGRESS ==p_flexed_key->dir)
    {
        if (!is_tcam)
        {
            drv_key_type = GetDsUserIdXKeyQuadHashKey(V, hashType0_f, pe->u.temp_entry->key);
        }
        else
        {
            drv_key_type = GetTempSclTcamXKeyQuad(V,sclKeyType0_f,pe->u.temp_entry->key);
        }
    }

    switch (p_flexed_key->key_size)
    {
        case SCL_KEY_USW_SIZE_80:
        if(CTC_INGRESS ==p_flexed_key->dir && !is_tcam)
        {
            SetDsUserIdXKeySingleHashKey(V,xKeyValid_f, pe->u.temp_entry->key,1);
            SetDsUserIdXKeySingleHashKey(V,xKeyValid_f, pe->u.temp_entry->mask,1);
        }
        break;

        case SCL_KEY_USW_SIZE_160:
        if(CTC_INGRESS ==p_flexed_key->dir)
        {
            if(!is_tcam)
            {
                SetDsUserIdXKeyDoubleHashKey(V,xKeyValid0_f, pe->u.temp_entry->key,1);
                SetDsUserIdXKeyDoubleHashKey(V,xKeyValid0_f, pe->u.temp_entry->mask,1);
                SetDsUserIdXKeyDoubleHashKey(V,xKeyValid1_f, pe->u.temp_entry->key,1);
                SetDsUserIdXKeyDoubleHashKey(V,xKeyValid1_f, pe->u.temp_entry->mask,1);
                SetDsUserIdXKeyDoubleHashKey(V,valid1_f, pe->u.temp_entry->key,1);
                SetDsUserIdXKeyDoubleHashKey(V,valid1_f, pe->u.temp_entry->mask,1);
                SetDsUserIdXKeyDoubleHashKey(V,hashType1_f, pe->u.temp_entry->key,drv_key_type);
                SetDsUserIdXKeyDoubleHashKey(V,hashType1_f, pe->u.temp_entry->mask,0xFF);
            }
            else
            {
                SetTempSclTcamXKeySingle(V,xKeyValid_f,pe->u.temp_entry->key,1);
                SetTempSclTcamXKeySingle(V,xKeyValid_f,pe->u.temp_entry->mask,1);
            }
        }
        else
        {
            SetDsEgressSclXHashKey(V,xKeyValid_f, pe->u.temp_entry->key,1);
            SetDsEgressSclXHashKey(V,xKeyValid_f, pe->u.temp_entry->mask,1);
        }
        break;

        case SCL_KEY_USW_SIZE_320:
        if(CTC_INGRESS ==p_flexed_key->dir)
        {
            if(!is_tcam)
            {
                SetDsUserIdXKeyQuadHashKey(V, xKeyValid0_f, pe->u.temp_entry->key, 1);
                SetDsUserIdXKeyQuadHashKey(V, xKeyValid0_f, pe->u.temp_entry->mask, 1);
                SetDsUserIdXKeyQuadHashKey(V, xKeyValid1_f, pe->u.temp_entry->key, 1);
                SetDsUserIdXKeyQuadHashKey(V, xKeyValid1_f, pe->u.temp_entry->mask, 1);
                SetDsUserIdXKeyQuadHashKey(V, xKeyValid2_f, pe->u.temp_entry->key, 1);
                SetDsUserIdXKeyQuadHashKey(V, xKeyValid2_f, pe->u.temp_entry->mask, 1);
                SetDsUserIdXKeyQuadHashKey(V, xKeyValid3_f, pe->u.temp_entry->key, 1);
                SetDsUserIdXKeyQuadHashKey(V, xKeyValid3_f, pe->u.temp_entry->mask, 1);
                SetDsUserIdXKeyQuadHashKey(V, valid1_f, pe->u.temp_entry->key, 1);
                SetDsUserIdXKeyQuadHashKey(V, valid1_f, pe->u.temp_entry->mask, 1);
                SetDsUserIdXKeyQuadHashKey(V, valid2_f, pe->u.temp_entry->key, 1);
                SetDsUserIdXKeyQuadHashKey(V, valid2_f, pe->u.temp_entry->mask, 1);
                SetDsUserIdXKeyQuadHashKey(V, valid3_f, pe->u.temp_entry->key, 1);
                SetDsUserIdXKeyQuadHashKey(V, valid3_f, pe->u.temp_entry->mask, 1);

                SetDsUserIdXKeyQuadHashKey(V, hashType1_f, pe->u.temp_entry->key, drv_key_type);
                SetDsUserIdXKeyQuadHashKey(V, hashType1_f, pe->u.temp_entry->mask, 0xFF);
                SetDsUserIdXKeyQuadHashKey(V, hashType2_f, pe->u.temp_entry->key, drv_key_type);
                SetDsUserIdXKeyQuadHashKey(V, hashType2_f, pe->u.temp_entry->mask, 0xFF);
                SetDsUserIdXKeyQuadHashKey(V, hashType3_f, pe->u.temp_entry->key, drv_key_type);
                SetDsUserIdXKeyQuadHashKey(V, hashType3_f, pe->u.temp_entry->mask, 0xFF);
            }
            else
            {
                SetTempSclTcamXKeyDouble(V,xKeyValid0_f,pe->u.temp_entry->key,1);
                SetTempSclTcamXKeyDouble(V,xKeyValid0_f,pe->u.temp_entry->mask,1);
                SetTempSclTcamXKeyDouble(V,xKeyValid1_f,pe->u.temp_entry->key,1);
                SetTempSclTcamXKeyDouble(V,xKeyValid1_f,pe->u.temp_entry->mask,1);

                SetTempSclTcamXKeyDouble(V,sclKeyType1_f,pe->u.temp_entry->key,drv_key_type);
                SetTempSclTcamXKeyDouble(V,sclKeyType1_f,pe->u.temp_entry->mask,DRV_ENUM(DRV_SCL_KEY_TYPE_MASK));
            }
        }
        break;

        case SCL_KEY_USW_SIZE_640:
            SetTempSclTcamXKeyQuad(V,xKeyValid0_f,pe->u.temp_entry->key,1);
            SetTempSclTcamXKeyQuad(V,xKeyValid0_f,pe->u.temp_entry->mask,1);
            SetTempSclTcamXKeyQuad(V,xKeyValid1_f,pe->u.temp_entry->key,1);
            SetTempSclTcamXKeyQuad(V,xKeyValid1_f,pe->u.temp_entry->mask,1);
            SetTempSclTcamXKeyQuad(V,xKeyValid2_f,pe->u.temp_entry->key,1);
            SetTempSclTcamXKeyQuad(V,xKeyValid2_f,pe->u.temp_entry->mask,1);
            SetTempSclTcamXKeyQuad(V,xKeyValid3_f,pe->u.temp_entry->key,1);
            SetTempSclTcamXKeyQuad(V,xKeyValid3_f,pe->u.temp_entry->mask,1);

            SetTempSclTcamXKeyQuad(V,sclKeyType1_f,pe->u.temp_entry->key,drv_key_type);
            SetTempSclTcamXKeyQuad(V,sclKeyType1_f,pe->u.temp_entry->mask,DRV_ENUM(DRV_SCL_KEY_TYPE_MASK));
            SetTempSclTcamXKeyQuad(V,sclKeyType2_f,pe->u.temp_entry->key,drv_key_type);
            SetTempSclTcamXKeyQuad(V,sclKeyType2_f,pe->u.temp_entry->mask,DRV_ENUM(DRV_SCL_KEY_TYPE_MASK));
            SetTempSclTcamXKeyQuad(V,sclKeyType3_f,pe->u.temp_entry->key,drv_key_type);
            SetTempSclTcamXKeyQuad(V,sclKeyType3_f,pe->u.temp_entry->mask,DRV_ENUM(DRV_SCL_KEY_TYPE_MASK));

        break;

        default:
        return CTC_E_INVALID_PARAM;
    }

    return CTC_E_NONE;
}

int32
sys_at_scl_build_flex_key_field(uint8 lchip, void* pKey_info, void* pe_info, uint8 is_add)
{
    uint32* p_data = NULL;
    uint32* p_mask = NULL;
    ctc_scl_kset_t* p_kset = NULL;
    sys_scl_sw_entry_t* pe = (sys_scl_sw_entry_t*)pe_info;
    sys_scl_flexed_key_t* pflex_key = (sys_scl_flexed_key_t*)(pe->u.temp_entry->fk);
    ctc_field_key_t*pKey = (ctc_field_key_t*)pKey_info;
    uint32 act_id;
    uint32 key_id;
    uint16 vlan_id;
    uint8 fwd_type = 0;
    uint8 is_svlan;
    uint8 i;
    uint32 data = 0;
    uint32 mask =  0xffffffff;
    uint32 udf_trunk[CTC_ACL_UDF_FIELD_NUM]= {0};
    uint32 udf_trunk_mask[CTC_ACL_UDF_FIELD_NUM]= {0};
    uint32 fk_udf[] = {SYS_FK_F_UDF_DATA0, SYS_FK_F_UDF_DATA1,
                         SYS_FK_F_UDF_DATA2, SYS_FK_F_UDF_DATA3,
                         SYS_FK_F_UDF_DATA4, SYS_FK_F_UDF_DATA5,
                         SYS_FK_F_UDF_DATA6, SYS_FK_F_UDF_DATA7};
    sys_acl_udf_info_t sys_udf_info;
    ctc_acl_udf_t* p_udf_data = NULL;
    ctc_acl_udf_t* p_udf_mask = NULL;
    ctc_vlan_range_info_t vrange_info;
    ctc_vlan_range_t      vlan_range;
    sys_xdata_fk_io_t xdata_fk;
    sys_scl_sw_entry_t temp_pe;

    CTC_PTR_VALID_CHECK(pKey);
    CTC_PTR_VALID_CHECK(pe);
    CTC_PTR_VALID_CHECK(pe->u.temp_entry);

    sal_memset(&sys_udf_info, 0 , sizeof(sys_udf_info));
    sal_memcpy(&temp_pe,pe,sizeof(sys_scl_sw_entry_t));
    sal_memset(&sys_udf_info,0,sizeof(sys_acl_udf_info_t));

    temp_pe.is_xkey = 0;
    CTC_ERROR_RETURN(_sys_usw_scl_get_table_id(lchip, (SCL_ENTRY_IS_TCAM(pe->key_type) ? 2 :0), &temp_pe,  &key_id, &act_id));
    xdata_fk.tbl_id = key_id;
    xdata_fk.type = (pe->direction ? CTC_XDATA_LOCAL_TYPE_EGS_SCL : CTC_XDATA_LOCAL_TYPE_SCL);
    p_data = (uint32*)pe->u.temp_entry->key;
    p_mask = (uint32*)pe->u.temp_entry->mask;
    p_kset = &pe->u.temp_entry->kset;
    xdata_fk.hash_type = SCL_ENTRY_IS_TCAM(pe->key_type) ? 0xff : 0;
    switch(pKey->type)
    {
        case SYS_SCL_FIELD_KEY_EXT_TYPE:
            xdata_fk.fk_field = SYS_FK_F_PR_EXT_TYPE;
            CTC_MAX_VALUE_CHECK(pKey->data, CTC_CONST16-1);
            if(SCL_ENTRY_IS_TCAM(pe->key_type))
            {
                SYS_SET_FK_FIELD(xdata_fk, is_add ? pKey->data : 0, is_add ? pKey->mask : 0);
            }
            else
            {
                SYS_SET_FK_FIELD(xdata_fk, pKey->data, mask);
                /* CTC_BMP_UNSET(p_kset->w, SYS_SCL_FIELD_KEY_EXT_TYPE); */ /* Useless now. To fix compilation error. */
            }
            break;
        case CTC_FIELD_KEY_L4_TYPE:
            CTC_MAX_VALUE_CHECK(pKey->data, CTC_CONST16-1);
            xdata_fk.fk_field = SYS_FK_F_PR_L4_TYPE;
            if(SCL_ENTRY_IS_TCAM(pe->key_type))
            {
                SYS_SET_FK_FIELD(xdata_fk, is_add ? pKey->data : 0, is_add ? pKey->mask : 0);
            }
            else
            {
                SYS_SET_FK_FIELD(xdata_fk, pKey->data, mask);
                CTC_BMP_UNSET(p_kset->w, CTC_FIELD_KEY_L4_TYPE);
            }

            break;
        case CTC_FIELD_KEY_L4_USER_TYPE:
            CTC_MAX_VALUE_CHECK(pKey->data, 0xB);
            xdata_fk.fk_field = SYS_FK_F_PR_L4_USER_TYPE;
            if(SCL_ENTRY_IS_TCAM(pe->key_type))
            {
                SYS_SET_FK_FIELD(xdata_fk, is_add ? pKey->data : 0, is_add ? pKey->mask : 0);
            }
            else
            {
                SYS_SET_FK_FIELD(xdata_fk, pKey->data, mask);
                CTC_BMP_UNSET(p_kset->w, CTC_FIELD_KEY_L4_USER_TYPE);
            }
            break;
         case CTC_FIELD_KEY_SVLAN_RANGE:
         case CTC_FIELD_KEY_CVLAN_RANGE:
            CTC_PTR_VALID_CHECK(pKey->ext_data);
            CTC_MAX_VALUE_CHECK(pKey->data, pKey->mask);
            SYS_SCL_VLAN_ID_CHECK(pKey->mask);

            vrange_info.direction = pe->direction;
            vrange_info.vrange_grpid = *((uint32*)(pKey->ext_data));
            vrange_info.block_id = 0;/*only support block 0, DsVlanRangeProfile*/
            vlan_range.is_acl = 0;
            vlan_range.vlan_start = pKey->data;
            vlan_range.vlan_end = pKey->mask;
            is_svlan = ((CTC_FIELD_KEY_SVLAN_RANGE == pKey->type) ? 1 : 0);
            CTC_ERROR_RETURN(sys_usw_vlan_get_maxvid_from_vrange(lchip, &vrange_info, &vlan_range, is_svlan ? TRUE : FALSE, &vlan_id));
            data = vlan_id;
            if(SCL_ENTRY_IS_TCAM(pe->key_type))
            {
                xdata_fk.fk_field = SYS_FK_F_VLAN_RANGE_MAX_LO;
                SYS_SET_FK_FIELD(xdata_fk, is_add ? (data & 0xff) : 0, is_add ? mask : 0);
                xdata_fk.fk_field = SYS_FK_F_VLAN_RANGE_MAX_HI;
                SYS_SET_FK_FIELD(xdata_fk, is_add ? ((data>>8)& 0xf) : 0, is_add ? mask : 0);
                xdata_fk.fk_field = SYS_FK_F_VLAN_RANGE_VALID;
                SYS_SET_FK_FIELD(xdata_fk, is_add ? 1 : 0, is_add ? 1 : 0);
                xdata_fk.fk_field = SYS_FK_F_VLAN_RANGE_TYPE;
                SYS_SET_FK_FIELD(xdata_fk, is_add ? is_svlan : 0, is_add ? 1 : 0);
            }
            else
            {
                xdata_fk.fk_field = SYS_FK_F_VLAN_RANGE_MAX_LO;
                SYS_SET_FK_FIELD(xdata_fk, (data & 0xff), mask);
                xdata_fk.fk_field = SYS_FK_F_VLAN_RANGE_MAX_HI;
                SYS_SET_FK_FIELD(xdata_fk, ((data>>8)& 0xf), mask);
                xdata_fk.fk_field = SYS_FK_F_VLAN_RANGE_VALID;
                SYS_SET_FK_FIELD(xdata_fk, 1, 1);
                xdata_fk.fk_field = SYS_FK_F_VLAN_RANGE_TYPE;
                SYS_SET_FK_FIELD(xdata_fk, is_svlan, 1);

                CTC_BMP_UNSET(p_kset->w, (is_svlan ? CTC_FIELD_KEY_SVLAN_RANGE : CTC_FIELD_KEY_CVLAN_RANGE));
            }
            pe->vrange_gid = vrange_info.vrange_grpid;
            break;
         case CTC_FIELD_KEY_UDF:
            CTC_PTR_VALID_CHECK(pKey->ext_data);
            CTC_PTR_VALID_CHECK(pKey->ext_mask);
            p_udf_data = (ctc_acl_udf_t*)pKey->ext_data;
            p_udf_mask = (ctc_acl_udf_t*)pKey->ext_mask;
            CTC_ERROR_RETURN(sys_usw_acl_get_udf_info(lchip, p_udf_data->udf_id, &sys_udf_info));
            if (!sys_udf_info.key_index_used)
            {
                CTC_ERROR_RETURN(CTC_E_NOT_EXIST);
            }
            if (sys_udf_info.is_sudf)
            {
                CTC_ERROR_RETURN(CTC_E_BADID);
            }
            if(SCL_ENTRY_IS_TCAM(pe->key_type))
            {
                xdata_fk.fk_field = SYS_FK_F_UDF_HIT_INDEX_LO;
                data = is_add ? sys_udf_info.udf_hit_index :0;
                SYS_SET_FK_FIELD(xdata_fk, data, is_add ? mask : 0);
                for (i = 0; i < CTC_ACL_UDF_FIELD_NUM; i++)
                {
                    if (!CTC_IS_BIT_SET(pflex_key->udf_bmp, i))
                    {
                        continue;
                    }
                    udf_trunk[i] = is_add ? ((1 << 16) | (p_udf_data->udf[i*2] << 8) | (p_udf_data->udf[i*2+1])): 0;
                    udf_trunk_mask[i] = is_add ? ((1 << 16) | (p_udf_mask->udf[i*2] << 8) | (p_udf_mask->udf[i*2+1])): 0;
                    xdata_fk.fk_field = fk_udf[i];
                    SYS_SET_FK_FIELD(xdata_fk, udf_trunk[i], udf_trunk_mask[i]);
                }
            }
            else
            {
                xdata_fk.fk_field = SYS_FK_F_UDF_HIT_INDEX_LO;
                data = sys_udf_info.udf_hit_index;
                SYS_SET_FK_FIELD(xdata_fk, data, mask);
                for (i = 0; i < CTC_ACL_UDF_FIELD_NUM; i++)
                {
                    if (!CTC_IS_BIT_SET(pflex_key->udf_bmp, i))
                    {
                        continue;
                    }
                    udf_trunk[i] = ((1 << 16) | (p_udf_data->udf[i*2] << 8) | (p_udf_data->udf[i*2+1]));
                    xdata_fk.fk_field = fk_udf[i];
                    SYS_SET_FK_FIELD(xdata_fk, udf_trunk[i], mask);
                }
                CTC_BMP_UNSET(p_kset->w, CTC_FIELD_KEY_UDF);
            }
            break;
        case CTC_FIELD_KEY_PKT_FWD_TYPE:
            CTC_MAX_VALUE_CHECK(pKey->data, CTC_ACL_PKT_FWD_TYPE_MAX-1);
            xdata_fk.fk_field = SYS_FK_F_PKT_FWD_TYPE;
            CTC_ERROR_RETURN(sys_usw_acl_map_fwd_type((uint8)pKey->data, &fwd_type));
            data = fwd_type;
            if(SCL_ENTRY_IS_TCAM(pe->key_type))
            {
                SYS_SET_FK_FIELD(xdata_fk, is_add ? data : 0, is_add ? mask : 0);
            }
            else
            {
                SYS_SET_FK_FIELD(xdata_fk, data, mask);
                CTC_BMP_UNSET(p_kset->w, CTC_FIELD_KEY_PKT_FWD_TYPE);
            }
            break;
        case CTC_FIELD_KEY_DST_CID:
            CTC_MAX_VALUE_CHECK(pKey->data, MCHIP_CAP(SYS_CAP_ACL_MAX_CID_VALUE));
            xdata_fk.fk_field = SYS_FK_F_DST_CID;
            if (SCL_ENTRY_IS_TCAM(pe->key_type))
            {
                SYS_SET_FK_FIELD(xdata_fk, is_add ? pKey->data : 0, is_add ? pKey->mask : 0);
            }
            else
            {
                SYS_SET_FK_FIELD(xdata_fk, pKey->data, pKey->mask);
                CTC_BMP_UNSET(p_kset->w, CTC_FIELD_KEY_DST_CID);
            }
            break;

         case CTC_FIELD_KEY_IP_HDR_ERROR:
             CTC_MAX_VALUE_CHECK(pKey->data, 0x1);
             xdata_fk.fk_field = SYS_FK_F_PR_IP_HDR_ERROR;
             if (SCL_ENTRY_IS_TCAM(pe->key_type))
             {
                 SYS_SET_FK_FIELD(xdata_fk, is_add ? pKey->data : 0, is_add ? pKey->mask : 0);
             }
             else
             {
                 SYS_SET_FK_FIELD(xdata_fk, pKey->data, pKey->mask);
                 CTC_BMP_UNSET(p_kset->w, CTC_FIELD_KEY_IP_HDR_ERROR);
             }
             break;
         case CTC_FIELD_KEY_L2_TYPE:
             CTC_MAX_VALUE_CHECK(pKey->data, 0x7);
             xdata_fk.fk_field = SYS_FK_F_PR_L2_TYPE;
             if (SCL_ENTRY_IS_TCAM(pe->key_type))
             {
                 SYS_SET_FK_FIELD(xdata_fk, is_add ? pKey->data : 0, is_add ? pKey->mask : 0);
             }
             else
             {
                 SYS_SET_FK_FIELD(xdata_fk, pKey->data, pKey->mask);
                 CTC_BMP_UNSET(p_kset->w, CTC_FIELD_KEY_L2_TYPE);
             }
             break;
         case CTC_FIELD_KEY_L3_TYPE:
             CTC_MAX_VALUE_CHECK(pKey->data, 0xF);
             xdata_fk.fk_field = SYS_FK_F_PR_L3_TYPE;
             if (SCL_ENTRY_IS_TCAM(pe->key_type))
             {
                 SYS_SET_FK_FIELD(xdata_fk, is_add ? pKey->data : 0, is_add ? pKey->mask : 0);
             }
             else
             {
                 SYS_SET_FK_FIELD(xdata_fk, pKey->data, pKey->mask);
                 CTC_BMP_UNSET(p_kset->w, CTC_FIELD_KEY_L3_TYPE);
             }
             break;
         case CTC_FIELD_KEY_VLAN_NUM:
             CTC_MAX_VALUE_CHECK(pKey->data, 0x3);
             xdata_fk.fk_field = SYS_FK_F_PR_VLAN_NUM;
             if (SCL_ENTRY_IS_TCAM(pe->key_type))
             {
                 SYS_SET_FK_FIELD(xdata_fk, is_add ? pKey->data : 0, is_add ? pKey->mask : 0);
             }
             else
             {
                 SYS_SET_FK_FIELD(xdata_fk, pKey->data, pKey->mask);
                 CTC_BMP_UNSET(p_kset->w, CTC_FIELD_KEY_VLAN_NUM);
             }
             break;
         case CTC_FIELD_KEY_IP_FRAG:
             CTC_MAX_VALUE_CHECK(pKey->data, CTC_IP_FRAG_MAX-1);
             xdata_fk.fk_field = SYS_FK_F_PR_FRAG_INFO;
             if (SCL_ENTRY_IS_TCAM(pe->key_type))
             {
                 SYS_SET_FK_FIELD(xdata_fk, is_add ? pKey->data : 0, is_add ? pKey->mask : 0);
             }
             else
             {
                 SYS_SET_FK_FIELD(xdata_fk, pKey->data, pKey->mask);
                 CTC_BMP_UNSET(p_kset->w, CTC_FIELD_KEY_IP_FRAG);
             }
             break;
         case CTC_FIELD_KEY_XDATA:
            CTC_PTR_VALID_CHECK(pKey->ext_data);
            xdata_fk.xdata = pKey->ext_data;
            xdata_fk.fk_field = SYS_FK_F_XDATA;
            for (i = 0; i < xdata_fk.xdata->num; i++)
            if (SCL_ENTRY_IS_TCAM(pe->key_type))
            {
                SYS_SET_FK_FIELD(xdata_fk, is_add ? 1 : 0, is_add ? 0xffff : 0);
            }
            else
            {
                SYS_SET_FK_FIELD(xdata_fk, is_add ? 1 : 0, is_add ? 0xffff : 0);
                CTC_BMP_UNSET(p_kset->w, CTC_FIELD_KEY_XDATA);
            }
            break;

         default:
            SYS_SCL_DBG_OUT(CTC_DEBUG_LEVEL_ERROR, " API or some feature is not supported \n");
            return CTC_E_NOT_SUPPORT;
    }
    return CTC_E_NONE;
}

int32
sys_at_scl_get_flex_key_field(uint8 lchip, sys_xdata_fk_io_t xdata_fk, sys_scl_sw_entry_t* pe, ctc_field_key_t* pKey)
{
    sys_scl_flexed_key_t* flexed_key = (sys_scl_flexed_key_t*)(pe->u.temp_entry->fk);
    uint32* p_data = pe->u.temp_entry->key;
    uint32* p_mask = pe->u.temp_entry->mask;
    uint32 value_array[4] = {0};
    uint32 mask_array[4] = {0};
    uint32 value = 0;
    uint32 mask = 0;
    uint32 vlan_id = 0;
    uint8 is_svlan = 0;
    uint8 i = 0;
    uint8 show_key;
    ctc_vlan_range_info_t vrange_info;
    ctc_vlan_range_t vlan_range;
    uint32 fk_udf[] = {SYS_FK_F_UDF_DATA0, SYS_FK_F_UDF_DATA1,
                         SYS_FK_F_UDF_DATA2, SYS_FK_F_UDF_DATA3,
                         SYS_FK_F_UDF_DATA4, SYS_FK_F_UDF_DATA5,
                         SYS_FK_F_UDF_DATA6, SYS_FK_F_UDF_DATA7};
    _sys_usw_scl_map_key_field_type(lchip, pe, pKey->type, &show_key);
    if (!CTC_BMP_ISSET(flexed_key->kset.w, pKey->type) || !CTC_IS_BIT_SET(pe->key_bmp, show_key))
    {
        return CTC_E_NOT_EXIST;
    }
    xdata_fk.hash_type = SCL_ENTRY_IS_TCAM(pe->key_type) ? 0xff : 0;
    pKey->data = 0;
    pKey->mask = 0;
    switch (pKey->type)
    {
        case SYS_SCL_FIELD_KEY_EXT_TYPE:
            xdata_fk.fk_field = SYS_FK_F_PR_EXT_TYPE;
            SYS_GET_FK_FIELD(xdata_fk, pKey->data, pKey->mask);
            break;
        case CTC_FIELD_KEY_L4_TYPE:
            xdata_fk.fk_field = SYS_FK_F_PR_L4_TYPE;
            SYS_GET_FK_FIELD(xdata_fk, pKey->data, pKey->mask);
            break;
        case CTC_FIELD_KEY_L4_USER_TYPE:
            xdata_fk.fk_field = SYS_FK_F_PR_L4_USER_TYPE;
            SYS_GET_FK_FIELD(xdata_fk, pKey->data, pKey->mask);
            break;
        case CTC_FIELD_KEY_SVLAN_RANGE:
        case CTC_FIELD_KEY_CVLAN_RANGE:
            sal_memset(&vlan_range, 0,sizeof(ctc_vlan_range_t));
            xdata_fk.fk_field = SYS_FK_F_VLAN_RANGE_MAX_LO;
            SYS_GET_FK_FIELD(xdata_fk, value_array[0], mask_array[0]);
            vlan_id = (value_array[0] & 0xff);
            xdata_fk.fk_field = SYS_FK_F_VLAN_RANGE_MAX_HI;
            SYS_GET_FK_FIELD(xdata_fk, value_array[1], mask_array[1]);
            vlan_id = (vlan_id | ((value_array[1] & 0xf)<< 8));
            xdata_fk.fk_field = SYS_FK_F_VLAN_RANGE_TYPE;
            SYS_GET_FK_FIELD(xdata_fk, value_array[2], mask_array[2]);
            is_svlan = value_array[2] ? TRUE : FALSE;

            vrange_info.block_id = 0;
            vrange_info.direction = pe->direction;
            vrange_info.vrange_grpid = pe->vrange_gid;
            sys_usw_vlan_get_vlan_range_by_maxvid(lchip, &vrange_info, vlan_id, is_svlan, &vlan_range);
            pKey->data = vlan_range.vlan_start;
            pKey->mask = vlan_range.vlan_end;
            break;
        case CTC_FIELD_KEY_UDF:
            for (i = 0; i < CTC_ACL_UDF_FIELD_NUM; i++)
            {
                if (!CTC_IS_BIT_SET(flexed_key->udf_bmp, i))
                {
                    continue;
                }
                xdata_fk.fk_field = fk_udf[i];
                SYS_GET_FK_FIELD(xdata_fk, value, mask);
                value_array[i/2] |= (value & 0xffff)<<((i%2)*16);
                mask_array[i/2] |= (mask & 0xffff)<<((i%2)*16);
            }
            SYS_USW_SET_USR_UDF(1, (uint8*)(pKey->ext_data), (uint32*)(value_array));
            SYS_USW_SET_USR_UDF(1, (uint8*)(pKey->ext_mask), (uint32*)(mask_array));
            break;
        case CTC_FIELD_KEY_PKT_FWD_TYPE:
            xdata_fk.fk_field = SYS_FK_F_PKT_FWD_TYPE;
            SYS_GET_FK_FIELD(xdata_fk, pKey->data, pKey->mask);
            break;
        case CTC_FIELD_KEY_DST_CID:
             xdata_fk.fk_field = SYS_FK_F_DST_CID;
            SYS_GET_FK_FIELD(xdata_fk, pKey->data, pKey->mask);
            break;
		case CTC_FIELD_KEY_VLAN_NUM:
             xdata_fk.fk_field = SYS_FK_F_PR_VLAN_NUM;
            SYS_GET_FK_FIELD(xdata_fk, pKey->data, pKey->mask);
            break;
        case CTC_FIELD_KEY_L3_TYPE:
             xdata_fk.fk_field = SYS_FK_F_PR_L3_TYPE;
            SYS_GET_FK_FIELD(xdata_fk, pKey->data, pKey->mask);
            break;
        case CTC_FIELD_KEY_L2_TYPE:
             xdata_fk.fk_field = SYS_FK_F_PR_L2_TYPE;
            SYS_GET_FK_FIELD(xdata_fk, pKey->data, pKey->mask);
            break;
        case CTC_FIELD_KEY_IP_FRAG:
             xdata_fk.fk_field = SYS_FK_F_PR_FRAG_INFO;
            SYS_GET_FK_FIELD(xdata_fk, pKey->data, pKey->mask);
            break;
        case CTC_FIELD_KEY_IP_HDR_ERROR:
             xdata_fk.fk_field = SYS_FK_F_PR_IP_HDR_ERROR;
            SYS_GET_FK_FIELD(xdata_fk, pKey->data, pKey->mask);
            break;
        case CTC_FIELD_KEY_XDATA:
            xdata_fk.fk_field = SYS_FK_F_XDATA;
            xdata_fk.xdata = (ctc_xdata_t*)pKey->ext_data;
            CTC_ERROR_RETURN(MCHIP_XDATA(lchip)->get_fk_field(lchip, &xdata_fk, p_data, &(pKey->data)));
            break;
        default:
            return CTC_E_INVALID_PARAM;
    }
    return CTC_E_NONE;
}
int32
sys_at_scl_show_flex_key(uint8 lchip, void* data, uint32* key_id, uint32* ad_id)
{
    int32 ret = CTC_E_NONE;
    uint32 value_array[8] = {0};
    uint32 mask_array[8] = {0};
    uint8 value = 0;
    uint8 loop = 0;
    uint16 gid = 0;
    sys_scl_sw_entry_t* pe = (sys_scl_sw_entry_t*)data;
    sys_scl_sw_entry_t temp_pe;
    sys_xdata_fk_io_t xdata_fk;
    ctc_field_key_t pKey;
    ctc_xdata_t xdata;
    ctc_xdata_field_t field[32];
    sys_scl_kset_t* p_kset_base = NULL;
    sys_scl_flexed_key_t* flexed_key = (sys_scl_flexed_key_t*)(pe->u.temp_entry->fk);
    uint8 is_tcam = SCL_ENTRY_IS_TCAM(pe->key_type);

    sal_memset(&pKey,0, sizeof(ctc_field_key_t));
    sal_memset(&xdata_fk,0, sizeof(sys_xdata_fk_io_t));
    sal_memset(&xdata,0, sizeof(ctc_xdata_t));
    sal_memset(field,0, sizeof(ctc_xdata_field_t)*32);
    sal_memcpy(&temp_pe, pe, sizeof(sys_scl_sw_entry_t));

    xdata.fields = field;
    p_kset_base = p_usw_scl_master[lchip]->kset_db[pe->direction][pe->key_type];
    if (!p_kset_base)
    {
        return CTC_E_NONE;
    }
#define SYS_SCL_FLEX_KEY_FIELD_EXT(gid) (CTC_BMP_ISSET(flexed_key->kset.w, gid) && !CTC_BMP_ISSET(p_kset_base->w, gid))
    temp_pe.is_xkey = 0;
    _sys_usw_scl_get_table_id(lchip, (SCL_ENTRY_IS_TCAM(temp_pe.key_type) ? 2 :0), &temp_pe, key_id, ad_id);

    xdata_fk.tbl_id = *key_id;
    xdata_fk.type = temp_pe.direction ? CTC_XDATA_LOCAL_TYPE_EGS_SCL: CTC_XDATA_LOCAL_TYPE_SCL;

    gid = CTC_FIELD_KEY_L4_TYPE;
    if (SYS_SCL_FLEX_KEY_FIELD_EXT(gid))
    {
        pKey.type = gid;
        ret = sys_at_scl_get_flex_key_field(lchip, xdata_fk, pe, &pKey);
        if (ret && ret != CTC_E_NOT_EXIST)
        {
            return ret;
        }
        else if (ret == CTC_E_NONE)
        {
            value = sys_usw_l4_type_map(lchip, pKey.data, FALSE);
            if (is_tcam)
            {
                SYS_SCL_DBG_OUT(CTC_DEBUG_LEVEL_DUMP, "  %-16s: 0x%x/0x%x \n", "l4-type", value, pKey.mask);
            }
            else
            {
                SYS_SCL_DBG_OUT(CTC_DEBUG_LEVEL_DUMP, "  %-16s: %u\n", "l4-type", value);
            }
        }
    }

    gid = CTC_FIELD_KEY_L4_USER_TYPE;
    if (SYS_SCL_FLEX_KEY_FIELD_EXT(gid))
    {
        pKey.type = gid;
        ret = sys_at_scl_get_flex_key_field(lchip, xdata_fk, pe, &pKey);
        if (ret && ret != CTC_E_NOT_EXIST)
        {
            return ret;
        }
        else if (ret == CTC_E_NONE)
        {
            value = sys_usw_l4_user_type_map(lchip, pKey.data, FALSE);
            if (is_tcam)
            {
                SYS_SCL_DBG_OUT(CTC_DEBUG_LEVEL_DUMP, "  %-16s: 0x%x/0x%x \n", "l4-user-type", value, pKey.mask);
            }
            else
            {
                SYS_SCL_DBG_OUT(CTC_DEBUG_LEVEL_DUMP, "  %-16s: %u\n", "l4-user-type", value);
            }
        }
    }

    gid = CTC_FIELD_KEY_PKT_FWD_TYPE;
    if (SYS_SCL_FLEX_KEY_FIELD_EXT(gid))
    {
        pKey.type = gid;
        ret = sys_at_scl_get_flex_key_field(lchip, xdata_fk, pe, &pKey);
        if (ret && ret != CTC_E_NOT_EXIST)
        {
            return ret;
        }
        else if (ret == CTC_E_NONE)
        {
            value = 0;
            sys_usw_acl_unmap_fwd_type((uint8)pKey.data, &value);
            if (is_tcam)
            {
                SYS_SCL_DBG_OUT(CTC_DEBUG_LEVEL_DUMP, "  %-16s: 0x%x/0x%x \n", "fwd-type", value, pKey.mask);
            }
            else
            {
                SYS_SCL_DBG_OUT(CTC_DEBUG_LEVEL_DUMP, "  %-16s: %u\n", "fwd-type", value);
            }
        }
    }

    gid = CTC_FIELD_KEY_SVLAN_RANGE;
    if (SYS_SCL_FLEX_KEY_FIELD_EXT(gid))
    {
        pKey.type = gid;
        ret = sys_at_scl_get_flex_key_field(lchip, xdata_fk, pe, &pKey);
        if (ret && ret != CTC_E_NOT_EXIST)
        {
            return ret;
        }
        else if (ret == CTC_E_NONE)
        {
            SYS_SCL_DBG_OUT(CTC_DEBUG_LEVEL_DUMP, "  %-16s: %u - %u \n", "svlan-range", pKey.data, pKey.mask);
        }
    }

    gid = CTC_FIELD_KEY_CVLAN_RANGE;
    if (SYS_SCL_FLEX_KEY_FIELD_EXT(gid))
    {
        pKey.type = gid;
        ret = sys_at_scl_get_flex_key_field(lchip, xdata_fk, pe, &pKey);
        if (ret && ret != CTC_E_NOT_EXIST)
        {
            return ret;
        }
        else if (ret == CTC_E_NONE)
        {
            SYS_SCL_DBG_OUT(CTC_DEBUG_LEVEL_DUMP, "  %-16s: %u - %u \n", "cvlan-range", pKey.data, pKey.mask);
        }
    }

    gid = CTC_FIELD_KEY_DST_CID;
    if (SYS_SCL_FLEX_KEY_FIELD_EXT(gid))
    {
        pKey.type = gid;
        ret = sys_at_scl_get_flex_key_field(lchip, xdata_fk, pe, &pKey);
        if (ret && ret != CTC_E_NOT_EXIST)
        {
            return ret;
        }
        else if (ret == CTC_E_NONE)
        {
            if (is_tcam)
            {
                SYS_SCL_DBG_OUT(CTC_DEBUG_LEVEL_DUMP, "  %-16s: 0x%x/0x%x \n", "dst-cid", pKey.data, pKey.mask);
            }
            else
            {
                SYS_SCL_DBG_OUT(CTC_DEBUG_LEVEL_DUMP, "  %-16s: %u\n", "dst-cid", pKey.data);
            }
        }
    }

	gid = CTC_FIELD_KEY_VLAN_NUM;
    if (SYS_SCL_FLEX_KEY_FIELD_EXT(gid))
    {
        pKey.type = gid;
        ret = sys_at_scl_get_flex_key_field(lchip, xdata_fk, pe, &pKey);
        if (ret && ret != CTC_E_NOT_EXIST)
        {
            return ret;
        }
        else if (ret == CTC_E_NONE)
        {
            if (is_tcam)
            {
                SYS_SCL_DBG_OUT(CTC_DEBUG_LEVEL_DUMP, "  %-16s: 0x%x/0x%x \n", "vlan-num", pKey.data, pKey.mask);
            }
            else
            {
                SYS_SCL_DBG_OUT(CTC_DEBUG_LEVEL_DUMP, "  %-16s: %u\n", "vlan-num", pKey.data);
            }
        }
    }
	
    gid = CTC_FIELD_KEY_L3_TYPE;
    if (SYS_SCL_FLEX_KEY_FIELD_EXT(gid))
    {
        pKey.type = gid;
        ret = sys_at_scl_get_flex_key_field(lchip, xdata_fk, pe, &pKey);
        if (ret && ret != CTC_E_NOT_EXIST)
        {
            return ret;
        }
        else if (ret == CTC_E_NONE)
        {
            if (is_tcam)
            {
                SYS_SCL_DBG_OUT(CTC_DEBUG_LEVEL_DUMP, "  %-16s: 0x%x/0x%x \n", "l3-type", pKey.data, pKey.mask);
            }
            else
            {
                SYS_SCL_DBG_OUT(CTC_DEBUG_LEVEL_DUMP, "  %-16s: %u\n", "l3-type", pKey.data);
            }
        }
    }
	
    gid = CTC_FIELD_KEY_L2_TYPE;
    if (SYS_SCL_FLEX_KEY_FIELD_EXT(gid))
    {
        pKey.type = gid;
        ret = sys_at_scl_get_flex_key_field(lchip, xdata_fk, pe, &pKey);
        if (ret && ret != CTC_E_NOT_EXIST)
        {
            return ret;
        }
        else if (ret == CTC_E_NONE)
        {
            if (is_tcam)
            {
                SYS_SCL_DBG_OUT(CTC_DEBUG_LEVEL_DUMP, "  %-16s: 0x%x/0x%x \n", "l2-type", pKey.data, pKey.mask);
            }
            else
            {
                SYS_SCL_DBG_OUT(CTC_DEBUG_LEVEL_DUMP, "  %-16s: %u\n", "l2-type", pKey.data);
            }
        }
    }
	
    gid = CTC_FIELD_KEY_IP_FRAG;
    if (SYS_SCL_FLEX_KEY_FIELD_EXT(gid))
    {
        pKey.type = gid;
        ret = sys_at_scl_get_flex_key_field(lchip, xdata_fk, pe, &pKey);
        if (ret && ret != CTC_E_NOT_EXIST)
        {
            return ret;
        }
        else if (ret == CTC_E_NONE)
        {
            if (is_tcam)
            {
                SYS_SCL_DBG_OUT(CTC_DEBUG_LEVEL_DUMP, "  %-16s: 0x%x/0x%x \n", "ip-frag", pKey.data, pKey.mask);
            }
            else
            {
                SYS_SCL_DBG_OUT(CTC_DEBUG_LEVEL_DUMP, "  %-16s: %u\n", "ip-frag", pKey.data);
            }
        }
    }
    
    gid = CTC_FIELD_KEY_IP_HDR_ERROR;
    if (SYS_SCL_FLEX_KEY_FIELD_EXT(gid))
    {
        pKey.type = gid;
        ret = sys_at_scl_get_flex_key_field(lchip, xdata_fk, pe, &pKey);
        if (ret && ret != CTC_E_NOT_EXIST)
        {
            return ret;
        }
        else if (ret == CTC_E_NONE)
        {
            if (is_tcam)
            {
                SYS_SCL_DBG_OUT(CTC_DEBUG_LEVEL_DUMP, "  %-16s: 0x%x/0x%x \n", "ip-hdr-error", pKey.data, pKey.mask);
            }
            else
            {
                SYS_SCL_DBG_OUT(CTC_DEBUG_LEVEL_DUMP, "  %-16s: %u\n", "ip-hdr-error", pKey.data);
            }
        }
    }   
	
    gid = CTC_FIELD_KEY_UDF;
    if (SYS_SCL_FLEX_KEY_FIELD_EXT(gid))
    {
        sal_memset(value_array, 0, sizeof(value_array));
        sal_memset(mask_array, 0, sizeof(mask_array));
        pKey.type = gid;
        pKey.ext_data = value_array;
        pKey.ext_mask = mask_array;
        ret = sys_at_scl_get_flex_key_field(lchip, xdata_fk, pe, &pKey);
        if (ret && ret != CTC_E_NOT_EXIST)
        {
            return ret;
        }
        else if (ret == CTC_E_NONE)
        {
            SYS_SCL_DBG_OUT(CTC_DEBUG_LEVEL_DUMP, "  %-16s: %s", "UDF", sys_usw_acl_output_udf((uint8*)&value_array[0]));
            SYS_SCL_DBG_OUT(CTC_DEBUG_LEVEL_DUMP, "%s", sys_usw_acl_output_udf((uint8*)&value_array[CTC_ACL_UDF_BYTE_NUM/8]));
            if (is_tcam)
            {
                SYS_SCL_DBG_OUT(CTC_DEBUG_LEVEL_DUMP, "/%s", sys_usw_acl_output_udf((uint8*)&mask_array[0]));
                SYS_SCL_DBG_OUT(CTC_DEBUG_LEVEL_DUMP, "%s\n", sys_usw_acl_output_udf((uint8*)&mask_array[CTC_ACL_UDF_BYTE_NUM/8]));
            }
            else
            {
                SYS_SCL_DBG_OUT(CTC_DEBUG_LEVEL_DUMP, "\n");
            }
        }
    }
    gid = CTC_FIELD_KEY_XDATA;
    if (SYS_SCL_FLEX_KEY_FIELD_EXT(gid))
    {
        sal_memset(value_array, 0, sizeof(value_array));
        sal_memset(mask_array, 0, sizeof(mask_array));
        pKey.type = gid;
        pKey.ext_data = &xdata;
        ret = sys_at_scl_get_flex_key_field(lchip, xdata_fk, pe, &pKey);
        if (ret && ret != CTC_E_NOT_EXIST)
        {
            return ret;
        }
        else if (ret == CTC_E_NONE)
        {
            SYS_SCL_DBG_OUT(CTC_DEBUG_LEVEL_DUMP, "  %-16s: %-6s %-6s %-6s\n", "XDATA", "WIDTH", "OFFSET","DATA");
            for (loop = 0; loop < xdata.num; loop++)
            {
                SYS_SCL_DBG_OUT(CTC_DEBUG_LEVEL_DUMP, "%24u %6u %6u\n", xdata.fields[loop].width, xdata.fields[loop].offset, xdata.fields[loop].data);
            }
        }
    }
    return CTC_E_NONE;
}
STATIC int32
_sys_at_scl_check_flex_key_uno(uint8 lchip, sys_scl_sw_entry_t* pe, ctc_scl_flex_key_t* p_scl_flex_key)
{
    uint16 loop;
    ctc_xdata_local_type_t type;
    ctc_scl_kset_t kset_base;
    ctc_scl_kset_t* p_kset = NULL;
    ctc_scl_kset_t* p_kset_user = NULL;
    ctc_xdata_field_t* p_field = NULL;

    CTC_ERROR_RETURN(_sys_usw_scl_check_action_type(lchip, pe));
    sal_memset(&kset_base, 0 , sizeof(kset_base));
    type = p_scl_flex_key->dir ? CTC_XDATA_LOCAL_TYPE_EGS_SCL: CTC_XDATA_LOCAL_TYPE_SCL;
    MCHIP_XDATA(lchip)->local_get_kset(lchip, type, &kset_base);

    p_kset = (ctc_scl_kset_t*)(p_usw_scl_master[lchip]->kset_db[pe->direction][pe->key_type]);
    if (NULL == p_kset)
    {
        SYS_SCL_DBG_OUT(CTC_DEBUG_LEVEL_ERROR, "Invalid key type, key_type:%u!\n", pe->key_type);
        return CTC_E_NOT_SUPPORT;
    }

    p_kset_user = &p_scl_flex_key->kset;

    for (loop = 0; loop < CTC_B2W_SIZE(CTC_FIELD_KEY_NUM); loop++)
    {
        /* check user kset and support kset */
        if(kset_base.w[loop] != (kset_base.w[loop]|p_kset_user->w[loop]) ||
            (CTC_FIELD_FLEX_KEY_MODE_REPLACE !=p_scl_flex_key->mode && (0 != (p_kset->w[loop] & p_kset_user->w[loop]))))
        {
            return CTC_E_INVALID_PARAM;
        }
    }

    /* check xdata width and offset */
    if(CTC_BMP_ISSET(p_scl_flex_key->kset.w, CTC_FIELD_KEY_XDATA))
    {
        CTC_PTR_VALID_CHECK(p_scl_flex_key->xdata);
        for(loop = 0; loop < p_scl_flex_key->xdata->num; loop++)
        {
            p_field = &p_scl_flex_key->xdata->fields[loop];
            switch(p_field->width)
            {
                case CTC_XDATA_WIDTH_4:
                case CTC_XDATA_WIDTH_8:
                case CTC_XDATA_WIDTH_16:
                    if((0 != p_field->offset % p_field->width)||(CTC_CONST128 < p_field->offset + p_field->width))
                    {
                        return CTC_E_INVALID_PARAM;
                    }
                break;
                default:
                    return CTC_E_INVALID_PARAM;
            }
        }
    }
    return CTC_E_NONE;
}

STATIC int32
_sys_at_scl_check_flex_key_param(uint8 lchip, ctc_scl_flex_key_t* p_scl_flex_key)
{
    CTC_MIN_VALUE_CHECK(p_scl_flex_key->key_type, SYS_SCL_XKEY_TYPE_BASE);
    CTC_MAX_VALUE_CHECK(p_scl_flex_key->origin_key_type, SYS_SCL_XKEY_TYPE_BASE-1);
    CTC_MAX_VALUE_CHECK(p_scl_flex_key->mode, CTC_FIELD_FLEX_KEY_MODE_MAX-1);
    if (CTC_BMP_ISSET(p_scl_flex_key->kset.w, CTC_FIELD_KEY_SVLAN_RANGE) && CTC_BMP_ISSET(p_scl_flex_key->kset.w, CTC_FIELD_KEY_CVLAN_RANGE))
    {
        SYS_SCL_DBG_OUT(CTC_DEBUG_LEVEL_ERROR, "SCL Xkey only support one type vlan range\n");
        return CTC_E_PARAM_CONFLICT;
    }
    return CTC_E_NONE;
}

int32
_sys_at_scl_set_flex_key(uint8 lchip, sys_scl_sw_entry_t* pe, sys_xdata_fk_t* p_fk, ctc_scl_flex_key_t* scl_flex_key,uint8* is_xkey)
{
    int32 ret = CTC_E_NONE;
    uint16 i;
    uint8 j;
    uint8 xpi_field_num = 0;
    uint8 isxkey = 0;
    uint8 fk_field[SYS_XDATA_FK_FIELD_NUM] = {0};

    for(i = 0; i < CTC_FIELD_KEY_NUM; i++)
    {
        if(!CTC_BMP_ISSET(scl_flex_key->kset.w, i))
        {
            continue;
        }
        sal_memset(&p_fk->info,0,sizeof(sys_xdata_fk_field_t));
        if (_sys_at_scl_map_fk_field_type(lchip, i, fk_field, scl_flex_key, &xpi_field_num))
        {
            continue;
        }
        p_fk->info.ptr_field_name = ifp_field_str[i];
        if(0 == xpi_field_num)
        {
            CTC_ERROR_GOTO(CTC_E_INVALID_PARAM, ret, error0);
        }
        for (j = 0; j < xpi_field_num; j++)
        {
            p_fk->info.field = fk_field[j];
            if (CTC_FIELD_KEY_XDATA == i)
            {
                p_fk->info.src_pos = scl_flex_key->xdata->fields[j].offset/CTC_XDATA_WIDTH_4;
                p_fk->info.width = scl_flex_key->xdata->fields[j].width;
                p_fk->info.mask = scl_flex_key->xdata->fields[j].mask;
            }
            CTC_ERROR_GOTO(MCHIP_XDATA(lchip)->add_fk(lchip, p_fk), ret, error0);
        }
        isxkey = 1;
    }
    p_fk->info.field = SYS_FK_F_FIELD_DONE;
    p_fk->info.ptr_field_name = "done";
    CTC_ERROR_GOTO(MCHIP_XDATA(lchip)->add_fk(lchip, p_fk), ret, error0);
    *is_xkey = isxkey;
    return CTC_E_NONE;
error0:
    if(ret != CTC_E_ENTRY_EXIST)
    {
        MCHIP_XDATA(lchip)->remove_fk(lchip, p_fk);
    }

    return ret;
}

int32
sys_at_scl_set_flex_key(uint8 lchip, void* scl_flex_key, uint8 inner)
{
    int32 ret = CTC_E_NONE;
    uint8  kset_is_empty = FALSE;
    ctc_scl_flex_key_t * p_scl_flex_key = (ctc_scl_flex_key_t*)scl_flex_key;
    sys_scl_flexed_key_t* p_flexed_key = NULL;
    sys_scl_flexed_key_t* fixed_key_new;
    sys_scl_kset_t* p_kset_base = NULL;
    sys_scl_sw_entry_t pe;
    ctc_scl_entry_t scl_entry;
    sys_xdata_fk_t xdata_fk;
    uint32 act_id;
    uint32 key_id;
    uint32 entry_size = 0;
    uint8 is_xkey = 0;
    uint8 loop = 0;

    CTC_ERROR_RETURN(_sys_at_scl_check_flex_key_param(lchip, p_scl_flex_key));
    sal_memset(&scl_entry,0,sizeof(ctc_scl_entry_t));
    sal_memset(&xdata_fk, 0, sizeof(sys_xdata_fk_t));

    kset_is_empty = _sys_at_scl_array_is_empty((uint8*)p_scl_flex_key->kset.w, CTC_B2W_SIZE(CTC_FIELD_KEY_NUM)*sizeof(uint32));

    p_flexed_key = ctc_vector_get(p_usw_scl_master[lchip]->flex_key_vec, p_scl_flex_key->key_type);

    if (!kset_is_empty && NULL != p_flexed_key)
    {   /*not support update*/
        return CTC_E_EXIST;
    }
    else if (kset_is_empty && NULL == p_flexed_key)
    {   /*do nothing*/
        return CTC_E_NONE;
    }
    else if (kset_is_empty && NULL != p_flexed_key)
    {   /*unset*/
        if (p_flexed_key->entry_count)
        {
            SYS_SCL_DBG_OUT(CTC_DEBUG_LEVEL_ERROR, "Flex key is in use, entry_count:%u!\n", p_flexed_key->entry_count);
            return CTC_E_IN_USE;
        }
        sal_memset(&pe,0,sizeof(sys_scl_sw_entry_t));
        pe.key_type = p_flexed_key->origin_key_type;
        pe.direction = p_flexed_key->dir;
        pe.action_type = p_flexed_key->dir ? CTC_SCL_ACTION_EGRESS :  CTC_SCL_ACTION_INGRESS;
        _sys_usw_scl_get_table_id(lchip, (SCL_ENTRY_IS_TCAM(p_flexed_key->origin_key_type) ? 2 :0), &pe, &key_id, &act_id);
        xdata_fk.tbl_id = key_id;
        xdata_fk.hash_type= SCL_ENTRY_IS_TCAM(p_flexed_key->origin_key_type) ? 0xff : 0;
        xdata_fk.type = p_flexed_key->dir ? CTC_XDATA_LOCAL_TYPE_EGS_SCL: CTC_XDATA_LOCAL_TYPE_SCL;
        MCHIP_XDATA(lchip)->remove_fk(lchip, &xdata_fk);

        SYS_USW_REGISTER_WB_SYNC_EN(lchip, CTC_FEATURE_SCL, SYS_WB_APPID_SCL_SUBID_FLEX_KEY, 1);
        ctc_vector_del(p_usw_scl_master[lchip]->flex_key_vec, p_flexed_key->key_type);
        mem_free(p_flexed_key);
        return CTC_E_NONE;
    }

    sal_memset(&pe, 0, sizeof(sys_scl_sw_entry_t));
    pe.direction = p_scl_flex_key->dir;
    if (inner)
    {
        pe.key_type = p_scl_flex_key->origin_key_type; /*sys_scl_key_type_t */
        pe.direction = p_scl_flex_key->dir;
    }
    else
    {
        scl_entry.key_type = p_scl_flex_key->origin_key_type;
        scl_entry.action_type = p_scl_flex_key->dir ? CTC_SCL_ACTION_EGRESS :  CTC_SCL_ACTION_INGRESS;
        CTC_ERROR_RETURN(_sys_usw_scl_map_key_action_type(lchip, &scl_entry, &pe));
    }
    CTC_ERROR_RETURN(_sys_at_scl_check_flex_key_uno(lchip, &pe, p_scl_flex_key));
    CTC_ERROR_RETURN(_sys_usw_scl_get_table_id(lchip, (SCL_ENTRY_IS_TCAM(pe.key_type) ? 2 :0), &pe, &key_id, &act_id));
    CTC_ERROR_RETURN(sys_usw_ftm_query_table_entry_size(lchip, key_id, &entry_size));

    xdata_fk.tbl_id = key_id;
    xdata_fk.hash_type= SCL_ENTRY_IS_TCAM(p_scl_flex_key->origin_key_type) ? 0xff : 0;
    xdata_fk.type = p_scl_flex_key->dir ? CTC_XDATA_LOCAL_TYPE_EGS_SCL: CTC_XDATA_LOCAL_TYPE_SCL;

    switch(p_scl_flex_key->mode)
    {
        case CTC_FIELD_FLEX_KEY_MODE_APPEND:/* append key*/
            if(SCL_ENTRY_IS_TCAM(pe.key_type))
            {
                return CTC_E_NOT_SUPPORT;
            }
        break;
        case CTC_FIELD_FLEX_KEY_MODE_DOUBLE_APPEND:/* double and append key*/
            if ((SCL_ENTRY_IS_TCAM(pe.key_type) && SCL_KEY_USW_SIZE_640 == entry_size) ||
                (!SCL_ENTRY_IS_TCAM(pe.key_type) && SCL_KEY_USW_SIZE_320 == entry_size))
            {
                return CTC_E_NOT_SUPPORT;
            }
        break;
        case CTC_FIELD_FLEX_KEY_MODE_REPLACE:/* replace key*/
        break;
        default:
            return CTC_E_INVALID_PARAM;
        break;

    }

    xdata_fk.mode = p_scl_flex_key->mode - 1;
    CTC_ERROR_RETURN(_sys_at_scl_set_flex_key(lchip, &pe, &xdata_fk, p_scl_flex_key, &is_xkey));

    MALLOC_ZERO(MEM_SCL_MODULE, fixed_key_new, sizeof(sys_scl_flexed_key_t));
    if (!fixed_key_new)
    {
        goto error1;
    }
    fixed_key_new->key_type = p_scl_flex_key->key_type;
    fixed_key_new->origin_key_type = pe.key_type;
    fixed_key_new->dir = p_scl_flex_key->dir;
    fixed_key_new->key_size = (p_scl_flex_key->dir == CTC_EGRESS)? SCL_KEY_USW_SIZE_160:(p_scl_flex_key->mode == CTC_FIELD_FLEX_KEY_MODE_DOUBLE_APPEND ? entry_size*2 : entry_size);
    fixed_key_new->mode = p_scl_flex_key->mode;
    fixed_key_new->udf_bmp = p_scl_flex_key->udf_bmp;
    fixed_key_new->is_xkey = is_xkey;
    fixed_key_new->is_replace = (p_scl_flex_key->mode == CTC_FIELD_FLEX_KEY_MODE_REPLACE || p_scl_flex_key->mode == CTC_FIELD_FLEX_KEY_MODE_APPEND);
    p_kset_base = (sys_scl_kset_t*)(p_usw_scl_master[lchip]->kset_db[pe.direction][pe.key_type]);
    if(CTC_FIELD_FLEX_KEY_MODE_REPLACE != fixed_key_new->mode)
    {
        for(loop = 0; loop < CTC_B2W_SIZE(CTC_FIELD_KEY_NUM); loop++)
        {
           fixed_key_new->kset.w[loop] = (p_scl_flex_key->kset.w[loop]| p_kset_base->w[loop]);
        }
    }
    else
    {
        sal_memcpy(&fixed_key_new->kset, &p_scl_flex_key->kset, sizeof(ctc_scl_kset_t));
    }

    SYS_USW_REGISTER_WB_SYNC_EN(lchip, CTC_FEATURE_SCL, SYS_WB_APPID_SCL_SUBID_FLEX_KEY, 1);
    if (FALSE == ctc_vector_add(p_usw_scl_master[lchip]->flex_key_vec, p_scl_flex_key->key_type, fixed_key_new))
    {
        ret = CTC_E_NO_MEMORY;
        SYS_SCL_DBG_OUT(CTC_DEBUG_LEVEL_ERROR, " [SCL] Hash insert fail\n");
        goto error2;
    }

    return CTC_E_NONE;
error2:
    mem_free(fixed_key_new);
error1:
    MCHIP_XDATA(lchip)->remove_fk(lchip, &xdata_fk);
    return ret;
}

int32
sys_at_scl_get_flex_key(uint8 lchip, void* scl_flex_key, uint8 inner)
{
    ctc_scl_flex_key_t * p_scl_flex_key = NULL;
    sys_scl_flexed_key_t* p_flexed_key = NULL;
    ctc_scl_entry_t scl_entry;
    sys_scl_sw_entry_t pe;
    
    p_scl_flex_key = (ctc_scl_flex_key_t*)scl_flex_key;
  
    if(p_scl_flex_key->key_type < SYS_SCL_XKEY_TYPE_BASE)
    {
        sal_memset(&scl_entry,0,sizeof(ctc_scl_entry_t));
        sal_memset(&pe,0,sizeof(sys_scl_sw_entry_t));
        scl_entry.key_type = p_scl_flex_key->key_type;
        CTC_ERROR_RETURN(_sys_usw_scl_map_key_action_type(lchip, &scl_entry, &pe));
        p_scl_flex_key->origin_key_type = pe.key_type;
        if(!p_usw_scl_master[lchip]->kset_db[p_scl_flex_key->dir][p_scl_flex_key->origin_key_type])
        {
            return  CTC_E_NOT_SUPPORT;
        }
        sal_memcpy(p_scl_flex_key->kset.w, p_usw_scl_master[lchip]->kset_db[p_scl_flex_key->dir][p_scl_flex_key->origin_key_type],
                    sizeof(uint32)*CTC_B2W_SIZE(CTC_FIELD_KEY_NUM));
    }
    else
    {
        p_flexed_key = ctc_vector_get(p_usw_scl_master[lchip]->flex_key_vec, p_scl_flex_key->key_type);
        if (NULL == p_flexed_key)
        {
            return CTC_E_NOT_EXIST;
        }
        sal_memcpy(p_scl_flex_key->kset.w, p_flexed_key->kset.w,sizeof(uint32)*CTC_B2W_SIZE(CTC_FIELD_KEY_NUM));
        p_scl_flex_key->dir = p_flexed_key->dir;
        CTC_ERROR_RETURN(_sys_usw_scl_map_sys_to_ctc_key_type(lchip, p_flexed_key->origin_key_type, &(p_scl_flex_key->origin_key_type)));
    }

   return CTC_E_NONE;
}

int32
sys_at_scl_get_flex_key_sets(uint8 lchip, void* scl_flex_key)
{
    ctc_scl_flex_key_t * p_scl_flex_key = (ctc_scl_flex_key_t*)scl_flex_key;
    ctc_scl_kset_t kset_base;
    ctc_xdata_local_type_t type;
    sys_scl_sw_entry_t pe;
    sys_xdata_fk_t p_fk;
    uint32 key_id = 0;
    uint32 act_id = 0;

    sal_memset(&pe,0,sizeof(sys_scl_sw_entry_t));
    sal_memset(&kset_base, 0 , sizeof(kset_base));
    sal_memset(&p_fk, 0 , sizeof(sys_xdata_fk_t));

    CTC_MAX_VALUE_CHECK(p_scl_flex_key->origin_key_type, SYS_SCL_XKEY_TYPE_BASE-1);
    CTC_VALUE_RANGE_CHECK(p_scl_flex_key->mode, CTC_FIELD_FLEX_KEY_MODE_APPEND, CTC_FIELD_FLEX_KEY_MODE_MAX-1);

    type = p_scl_flex_key->dir ? CTC_XDATA_LOCAL_TYPE_EGS_SCL: CTC_XDATA_LOCAL_TYPE_SCL;
    sys_usw_xdata_local_get_kset(lchip, type, &kset_base);

    pe.key_type = p_scl_flex_key->origin_key_type;
    pe.action_type = p_scl_flex_key->dir ? SYS_SCL_ACTION_EGRESS : SYS_SCL_ACTION_INGRESS;
    CTC_ERROR_RETURN(_sys_usw_scl_get_table_id(lchip, (SCL_ENTRY_IS_TCAM(p_scl_flex_key->origin_key_type) ? 2 :0), &pe, &key_id, &act_id));

    sal_memcpy(p_scl_flex_key->kset.w, &kset_base.w,sizeof(uint32)*CTC_B2W_SIZE(CTC_FIELD_KEY_NUM));

    p_fk.mode = p_scl_flex_key->mode -1;
    p_fk.hash_type = SCL_ENTRY_IS_TCAM(p_scl_flex_key->origin_key_type) ? 0xff : 0;
    p_fk.type = type;
    p_fk.tbl_id = key_id;
    if (MCHIP_XDATA(lchip)->fk_get_flex_bits)
    {
        CTC_ERROR_RETURN(MCHIP_XDATA(lchip)->fk_get_flex_bits(lchip, &p_fk));
    }
    p_scl_flex_key->flex_bits = p_fk.flex_bits;
    return CTC_E_NONE;
}


#endif

#endif


